diff --git a/ANDROID-CHANGES.txt b/ANDROID-CHANGES.txt
deleted file mode 100644
index d4cade0..0000000
--- a/ANDROID-CHANGES.txt
+++ /dev/null
@@ -1,8 +0,0 @@
-
-Change made for Android
-
-1) Change coverage.out.file location in core/res/emma_default.properties to /data/coverage.ec
-2) Remove reference to sun.misc.* in core/java14/com/vladium/util/IJREVersion.java
-3) Remove reference to sun.misc.* and SunJREExitHookManager class from core/java13/com/vladium/util/exit/ExitHookManager.java
-4) Add java.security.cert.Certificate cast to core/java12/com/vladium/emma/rt/InstrClassLoader.java to fix compiler error
-5) Copy /core/res/com/vladium/emma/rt/RTExitHook.closure into source tree so it does not have to be generated in the build
diff --git a/Android.mk b/Android.mk
deleted file mode 100644
index a8df511..0000000
--- a/Android.mk
+++ /dev/null
@@ -1,16 +0,0 @@
-# Copyright 2008 The Android Open Source Project
-
-LOCAL_PATH := $(my-dir)
-include $(CLEAR_VARS)
-
-LOCAL_SRC_FILES := $(call all-java-files-under, core)
-
-LOCAL_MODULE := emma
-
-LOCAL_MODULE_TAGS := tests
-
-LOCAL_JAVA_RESOURCE_DIRS := core/res
-
-LOCAL_NO_EMMA_INSTRUMENT := true
-
-include $(BUILD_JAVA_LIBRARY)
diff --git a/BUILD.txt b/BUILD.txt
deleted file mode 100644
index 60e7a58..0000000
--- a/BUILD.txt
+++ /dev/null
@@ -1,43 +0,0 @@
-
-REQUIREMENTS
-~~~~~~~~~~~~
-
-- JDK1.4 (the build will not work in JDK1.5)
-- Apache ANT 1.5+ (official build uses v1.6.1)
-
-BUILDING EMMA
-~~~~~~~~~~~~~
-
-- cd into the directory containing build.xml and create a file
-  "build.properties" that tells the build where your JDK and ANT are located:
-
-    - if Java 1.4 is not your currently installed Java version, set the
-      following property to point to the "jre" subdirectory of your JDK 1.4
-      install:
-
-build.target.j2se.14.home = <JDK 1.4 install>/jre
-
-    - if you don't have ANT_HOME environment variable set up to point to ANT
-    1.5 home directory, set the following property:
-
-build.target.ant.15.home = <ANT 1.5 install dir> 
-
-- From the directory containing build.xml, execute:
-
->ant
-
-- After a successful build, EMMA jars will be located in
-  ${basedir}/${dist.dir}, which defaults to ./dist
-
-
-- To remove all generated build artifacts and reset the build to a clean
-  state, execute:
-
->ant clean
-
- __________________________________________________________________________
-       Copyright (C) 2003-2004 Vlad Roubtsov. All rights reserved.
-
- This program and the accompanying materials are made available under
- the terms of the Common Public License v1.0 which accompanies this
- distribution, and is available at http://www.eclipse.org/legal/cpl-v10.html
diff --git a/TRACKING.txt b/TRACKING.txt
deleted file mode 100644
index 3ea627a..0000000
--- a/TRACKING.txt
+++ /dev/null
@@ -1,5 +0,0 @@
-
-fixed BUGs:
-
-1189166
-988160
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/ANTMain.java b/ant/ant14/com/vladium/emma/ANTMain.java
deleted file mode 100644
index bc36184..0000000
--- a/ant/ant14/com/vladium/emma/ANTMain.java
+++ /dev/null
@@ -1,39 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ANTMain.java,v 1.1.1.1 2004/05/09 16:57:26 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import com.vladium.emma.IAppConstants;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2004
- */
-public
-final class ANTMain
-{
-    // public: ................................................................
-    
-    
-    public static void main (final String [] args)
-    {
-        System.out.println ("this jar contains ANT task definitions for " + IAppConstants.APP_NAME
-            + " and is not meant to be executable");
-            
-        System.out.println ();
-        System.out.println (IAppConstants.APP_USAGE_BUILD_ID);
-    } 
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/ant/FileTask.java b/ant/ant14/com/vladium/emma/ant/FileTask.java
deleted file mode 100644
index 6357799..0000000
--- a/ant/ant14/com/vladium/emma/ant/FileTask.java
+++ /dev/null
@@ -1,136 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: FileTask.java,v 1.2.2.1 2004/07/08 10:52:10 vlad_r Exp $
- */
-package com.vladium.emma.ant;
-
-import java.io.File;
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-
-import org.apache.tools.ant.DirectoryScanner;
-import org.apache.tools.ant.types.FileSet;
-
-import com.vladium.emma.ant.XFileSet;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class FileTask extends NestedTask
-{
-    // public: ................................................................
-    
-    
-//    public static final class FileElement
-//    {
-//        public FileElement (final List /* File */ files)
-//        {
-//            m_files = files;
-//        }
-//        
-//        public void setFile (final File file)
-//        {
-//            if (file != null) m_files.add (file);
-//        }
-//        
-//        
-//        private final List /* File */ m_files;
-//        
-//    } // end of nested class
-    
-    
-    // infileset|fileset element:
-
-    public final void addInfileset (final XFileSet set)
-    {
-        if (set != null) m_dataFileSets.add (set);
-    }
-    
-    public final void addFileset (final XFileSet set)
-    {
-        if (set != null) m_dataFileSets.add (set);
-    }
-
-
-//    // infile|file element:
-//    
-//    public final FileElement createInfile ()
-//    {
-//        return new FileElement (m_dataFiles);
-//    }
-//    
-//    public final FileElement createFile ()
-//    {
-//        return new FileElement (m_dataFiles);
-//    }
-    
-    // protected: .............................................................
-    
-    
-    protected FileTask (final SuppressableTask parent)
-    {
-        super (parent);
-        
-        m_dataFileSets = new ArrayList ();
-//        m_dataFiles = new ArrayList ();
-    }
-
-
-    protected final String [] getDataPath (final boolean removeNonexistent)
-    {
-        final List /* String */ _files = new ArrayList ();
-            
-        // merge filesets:
-        for (Iterator i = m_dataFileSets.iterator (); i.hasNext (); )
-        {
-            final FileSet set = (FileSet) i.next ();
-            final DirectoryScanner ds = set.getDirectoryScanner (project);
-            final File dsBaseDir = ds.getBasedir ();
-            
-            final String [] dsfiles = ds.getIncludedFiles ();
-            for (int f = 0; f < dsfiles.length; ++ f)
-            {
-                _files.add (new File (dsBaseDir, dsfiles [f]).getAbsolutePath ());
-            }
-        }
-        
-//        // merge files:
-//        for (Iterator i = m_dataFiles.iterator (); i.hasNext (); )
-//        {
-//            final File file = (File) i.next ();
-//            if (! removeNonexistent || file.exists ())
-//            {
-//                _files.add (file.getAbsolutePath ());
-//            }
-//        }
-        
-        if (_files.size () == 0)
-            return EMPTY_STRING_ARRAY;
-        else
-        {            
-            final String [] files = new String [_files.size ()];
-            _files.toArray (files);
-            
-            return files;
-        }
-    }
-    
-    // package: ...............................................................
-    
-    // private: ...............................................................
-   
-    
-    private final List /* FileSet */ m_dataFileSets; // never null
-//    private final List /* File */ m_dataFiles; // never null
-    
-    private static final String [] EMPTY_STRING_ARRAY = new String [0];
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/ant/FilterTask.java b/ant/ant14/com/vladium/emma/ant/FilterTask.java
deleted file mode 100644
index 4af71e9..0000000
--- a/ant/ant14/com/vladium/emma/ant/FilterTask.java
+++ /dev/null
@@ -1,76 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: FilterTask.java,v 1.1.1.1.2.1 2004/07/08 10:52:10 vlad_r Exp $
- */
-package com.vladium.emma.ant;
-
-import java.io.File;
-
-import com.vladium.util.Strings;
-import com.vladium.emma.instr.FilterCfg;
-import com.vladium.emma.instr.FilterCfg.filterElement;
-
-import org.apache.tools.ant.BuildException;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class FilterTask extends NestedTask
-{
-    // public: ................................................................
-
-
-    public void init () throws BuildException
-    {
-        super.init ();
-        
-        m_filterCfg = new FilterCfg (this);
-    }
-
-    
-    // filter attribute/element:
-    
-    public final void setFilter (final String filter)
-    {
-        m_filterCfg.setFilter (filter);
-    }
-    
-    public final filterElement createFilter ()
-    {
-        return m_filterCfg.createFilter ();
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected FilterTask (final SuppressableTask parent)
-    {
-        super (parent);
-    }
-    
-    
-    protected final String [] getFilterSpecs ()
-    {
-        return m_filterCfg.getFilterSpecs ();
-    }
-        
-
-    protected static final String COMMA               = ",";
-    protected static final String COMMA_DELIMITERS    = COMMA + Strings.WHITE_SPACE;
-    protected static final String PATH_DELIMITERS     = COMMA.concat (File.pathSeparator);
-    
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-
-    private /*final*/ FilterCfg m_filterCfg;    
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/ant/GenericCfg.java b/ant/ant14/com/vladium/emma/ant/GenericCfg.java
deleted file mode 100644
index 02ebae6..0000000
--- a/ant/ant14/com/vladium/emma/ant/GenericCfg.java
+++ /dev/null
@@ -1,150 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: GenericCfg.java,v 1.1.1.1.2.1 2004/07/08 10:52:10 vlad_r Exp $
- */
-package com.vladium.emma.ant;
-
-import java.io.File;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Properties;
-
-import org.apache.tools.ant.BuildException;
-import org.apache.tools.ant.Task;
-
-import com.vladium.emma.EMMAProperties;
-import com.vladium.util.IProperties;
-import com.vladium.util.Property;
-
-// ----------------------------------------------------------------------------
-/**
- * GenericCfg is a simple container for 'generic' properties, i.e., properties
- * that are set via generic 'properties=&lt;file&gt;' attribute and &lt;property&gt;
- * nested elements. This class makes no decision about relative priorities for
- * propertie set in an external file or via nested elements, leaving this up
- * to the parent.
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-class GenericCfg
-{
-    // public: ................................................................
-    
-
-    public GenericCfg (final Task task)
-    {
-        if (task == null) throw new IllegalArgumentException ("null input: task");
-        
-        m_task = task;
-        m_genericPropertyElements = new ArrayList ();
-    }
-    
-
-    // .properties file attribute [actual file I/O done lazily by getFileSettings()]:
-    
-    public void setProperties (final File file)
-    {
-        m_settingsFile = file; // actual file I/O is done in getFileSettings()
-    }
-
-    // generic property element:
-    
-    public PropertyElement createProperty ()
-    {
-        m_genericSettings = null;
-        
-        final PropertyElement property = new PropertyElement ();
-        m_genericPropertyElements.add (property);
-        
-        return property;
-    }
-
-    // ACCESSORS:
-
-    public IProperties getFileSettings ()
-    {
-        IProperties fileSettings = m_fileSettings;
-        if ((fileSettings == null) && (m_settingsFile != null))
-        {
-            try
-            {
-                fileSettings = EMMAProperties.wrap (Property.getPropertiesFromFile (m_settingsFile));
-            }
-            catch (IOException ioe)
-            {
-                throw (BuildException) SuppressableTask.newBuildException (m_task.getTaskName ()
-                    + ": property file [" + m_settingsFile.getAbsolutePath () + "] could not be read" , ioe, m_task.getLocation ()).fillInStackTrace ();
-            }
-            
-            m_fileSettings = fileSettings;
-            
-            return fileSettings;
-        }
-        
-        return fileSettings;
-    }
-    
-    public IProperties getGenericSettings ()
-    {
-        IProperties genericSettings = m_genericSettings;
-        if (genericSettings == null)
-        {
-            genericSettings = EMMAProperties.wrap (new Properties ());
-            
-            for (Iterator i = m_genericPropertyElements.iterator (); i.hasNext (); )
-            {
-                final PropertyElement property = (PropertyElement) i.next ();
-                
-                final String name = property.getName ();
-                String value = property.getValue ();
-                if (value == null) value = "";
-                
-                if (name != null)
-                {
-                    // [assertion: name != null, value != null]
-                    
-                    final String currentValue = genericSettings.getProperty (name);  
-                    if ((currentValue != null) && ! value.equals (currentValue))
-                    {
-                        throw (BuildException) SuppressableTask.newBuildException (m_task.getTaskName ()
-                            + ": conflicting settings for property [" + name + "]: [" + value + "]" , m_task.getLocation ()).fillInStackTrace ();
-                    }
-                    else
-                    {
-                        genericSettings.setProperty (name, value);
-                    }
-                }
-            }
-            
-            m_genericSettings = genericSettings;
-            
-            return genericSettings;
-        }
-        
-        return genericSettings;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private final Task m_task;
-        
-    private final List /* PropertyElement */ m_genericPropertyElements; // never null
-    private File m_settingsFile; // can be null
-    
-    private transient IProperties m_fileSettings; // can be null
-    private transient IProperties m_genericSettings; // can be null
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/ant/NestedTask.java b/ant/ant14/com/vladium/emma/ant/NestedTask.java
deleted file mode 100644
index cd2c0ad..0000000
--- a/ant/ant14/com/vladium/emma/ant/NestedTask.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: NestedTask.java,v 1.1.1.1.2.1 2004/07/08 10:52:10 vlad_r Exp $
- */
-package com.vladium.emma.ant;
-
-import com.vladium.util.IProperties;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class NestedTask extends SuppressableTask
-{
-    // public: ................................................................
-    
-    // protected: .............................................................
-    
-    
-    protected NestedTask (final SuppressableTask parent)
-    {
-        if (parent == null)
-            throw new IllegalArgumentException ("null input: parent");
-        
-        m_parent = parent;
-    }
-
-    /**
-     * Overrides {@link SuppressableTask#getTaskSettings()} to mix in parent
-     * task settings as the base settings. 
-     */
-    protected final IProperties getTaskSettings ()
-    {
-        final IProperties parentSettings = m_parent != null
-            ? m_parent.getTaskSettings ()
-            : null;
-        
-        final IProperties taskOverrides = super.getTaskSettings ();
-        
-        // task settings are always more specific than parent settings, but attention
-        // needs to be paid to horizontal inheritance:
-        
-        if (parentSettings == null)
-            return taskOverrides;
-        else
-        {
-            final IProperties settings = IProperties.Factory.combine (taskOverrides, parentSettings);
-        
-            return settings;
-        }
-    }
-
-    
-    protected final SuppressableTask m_parent;
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/ant/PropertyElement.java b/ant/ant14/com/vladium/emma/ant/PropertyElement.java
deleted file mode 100644
index 2d002bc..0000000
--- a/ant/ant14/com/vladium/emma/ant/PropertyElement.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: PropertyElement.java,v 1.1.1.1.2.1 2004/07/10 03:34:52 vlad_r Exp $
- */
-package com.vladium.emma.ant;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class PropertyElement
-{
-    // public: ................................................................
-    
-    
-    public PropertyElement ()
-    {
-        // ensure the constructor is always public
-    }
-    
-
-    public String getName ()
-    {
-        return m_name;
-    }
-    
-    public String getValue ()
-    {
-        return m_value;
-    }
-
-    public void setName (final String name)
-    {
-        m_name = name;
-    }
-    
-    public void setValue (final String value)
-    {
-        m_value = value;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-
-    private String m_name, m_value;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/ant/StringValue.java b/ant/ant14/com/vladium/emma/ant/StringValue.java
deleted file mode 100644
index 454c2ce..0000000
--- a/ant/ant14/com/vladium/emma/ant/StringValue.java
+++ /dev/null
@@ -1,65 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: StringValue.java,v 1.2 2004/05/20 02:28:06 vlad_r Exp $
- */
-package com.vladium.emma.ant;
-
-import org.apache.tools.ant.Task;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class StringValue
-{
-    // public: ................................................................
-    
-    
-    public void appendValue (final String value, final String separator)
-    {
-        if ((value != null) && (value.length () > 0))
-        {
-            if (m_value == null)
-            {
-                m_value = new StringBuffer (value); 
-            }
-            else
-            {
-                m_value.append (separator);
-                m_value.append (value); // no trailing separator kept
-            }
-        }
-    }
-                
-    public String getValue ()
-    {
-        return m_value != null ? m_value.toString () : null;  
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected StringValue (final Task task)
-    {
-        if (task == null) throw new IllegalArgumentException ("null input: task");
-        
-        m_task = task;
-    }
-
-
-    protected final Task m_task;
-    
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-    
-    private StringBuffer m_value;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/ant/SuppressableTask.java b/ant/ant14/com/vladium/emma/ant/SuppressableTask.java
deleted file mode 100644
index ff90e58..0000000
--- a/ant/ant14/com/vladium/emma/ant/SuppressableTask.java
+++ /dev/null
@@ -1,132 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: SuppressableTask.java,v 1.1.1.1.2.2 2004/07/16 23:32:04 vlad_r Exp $
- */
-package com.vladium.emma.ant;
-
-import java.io.File;
-
-import com.vladium.emma.IAppConstants;
-import com.vladium.util.IProperties;
-
-import org.apache.tools.ant.BuildException;
-import org.apache.tools.ant.Location;
-import org.apache.tools.ant.Task;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class SuppressableTask extends Task
-{
-    // public: ................................................................
-    
-    
-    public void init () throws BuildException
-    {
-        super.init ();
-        
-        m_verbosityCfg = new VerbosityCfg ();
-        m_genericCfg = new GenericCfg (this);
-    }
-
-    /**
-     * Set the optional 'enabled' attribute [defaults to 'true'].
-     */
-    public final void setEnabled (final boolean enabled)
-    {
-        m_enabled = enabled;
-    }
-    
-    public final boolean isEnabled ()
-    {
-        return m_enabled;
-    }
-    
-    // verbosity attribute:
-    
-    public void setVerbosity (final VerbosityCfg.VerbosityAttribute verbosity)
-    {
-        m_verbosityCfg.setVerbosity (verbosity);
-    }
-    
-    // verbosity class filter attribute:
-    
-    public void setVerbosityfilter (final String filter)
-    {
-        m_verbosityCfg.setVerbosityfilter (filter);
-    }
-
-    // .properties file attribute:
-    
-    public final void setProperties (final File file)
-    {
-        m_genericCfg.setProperties (file);
-    }
-
-    // generic property element:
-    
-    public final PropertyElement createProperty ()
-    {
-        return m_genericCfg.createProperty ();
-    }
-    
-    
-    public static BuildException newBuildException (final String msg, final Location location)
-    {
-        final String prefixedMsg = ((msg == null) || (msg.length () == 0))
-            ? msg
-            : IAppConstants.APP_THROWABLE_BUILD_ID + " " + msg;
-       
-        return new BuildException (prefixedMsg, location); 
-    }
-    
-    public static BuildException newBuildException (final String msg, final Throwable cause, final Location location)
-    {
-        final String prefixedMsg = ((msg == null) || (msg.length () == 0))
-            ? msg
-            : IAppConstants.APP_THROWABLE_BUILD_ID + " " + msg;
-       
-        return new BuildException (prefixedMsg, cause, location); 
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected SuppressableTask ()
-    {
-        m_enabled = true; // by default, all tasks are enabled
-    }
-    
-    protected IProperties getTaskSettings ()
-    {
-        // (1) by default, generic settings are always more specific than any file settings
-        
-        // (2) verbosity settings use dedicated attributes and hence are more specific
-        // than anything generic
-        
-        final IProperties fileSettings = m_genericCfg.getFileSettings ();
-        final IProperties genericSettings = m_genericCfg.getGenericSettings (); 
-        final IProperties verbositySettings = m_verbosityCfg.getSettings ();
-        
-        return IProperties.Factory.combine (verbositySettings,
-               IProperties.Factory.combine (genericSettings,
-                                            fileSettings));
-    }    
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-    
-    
-    private /*final*/ VerbosityCfg m_verbosityCfg;
-    private /*final*/ GenericCfg m_genericCfg;
-    private boolean m_enabled;
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/ant/VerbosityCfg.java b/ant/ant14/com/vladium/emma/ant/VerbosityCfg.java
deleted file mode 100644
index 41d9842..0000000
--- a/ant/ant14/com/vladium/emma/ant/VerbosityCfg.java
+++ /dev/null
@@ -1,102 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: VerbosityCfg.java,v 1.1.2.1 2004/07/16 23:32:04 vlad_r Exp $
- */
-package com.vladium.emma.ant;
-
-import java.util.Properties;
-
-import org.apache.tools.ant.types.EnumeratedAttribute;
-
-import com.vladium.emma.AppLoggers;
-import com.vladium.emma.EMMAProperties;
-import com.vladium.logging.ILogLevels;
-import com.vladium.util.IProperties;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2004
- */
-public
-final class VerbosityCfg
-{
-    // public: ................................................................
-    
-
-    public static final class VerbosityAttribute extends EnumeratedAttribute
-    {
-        public String [] getValues ()
-        {
-            return VALUES;
-        }
-        
-        private static final String [] VALUES = new String []
-            {
-                ILogLevels.SEVERE_STRING,
-                ILogLevels.SILENT_STRING,
-                ILogLevels.WARNING_STRING,
-                ILogLevels.QUIET_STRING,
-                ILogLevels.INFO_STRING,
-                ILogLevels.VERBOSE_STRING,
-                ILogLevels.TRACE1_STRING,
-                ILogLevels.TRACE2_STRING,
-                ILogLevels.TRACE3_STRING,
-            };
-
-    } // end of nested class
-    
-
-    // verbosity attribute:
-    
-    public void setVerbosity (final VerbosityAttribute verbosity)
-    {
-        m_verbosity = verbosity.getValue ();
-    }
-    
-    // verbosity class filter attribute:
-    
-    public void setVerbosityfilter (final String filter)
-    {
-        m_verbosityFilter = filter;
-    }
-    
-    // ACCESSORS:
-    
-    public IProperties getSettings ()
-    {
-        IProperties settings = m_settings;
-        if (settings == null)
-        {
-            settings = EMMAProperties.wrap (new Properties ());
-            
-            if ((m_verbosity != null) && (m_verbosity.trim ().length () > 0))
-                settings.setProperty (AppLoggers.PROPERTY_VERBOSITY_LEVEL, m_verbosity.trim ());
-            
-            if ((m_verbosityFilter != null) && (m_verbosityFilter.trim ().length () > 0))
-                settings.setProperty (AppLoggers.PROPERTY_VERBOSITY_FILTER, m_verbosityFilter.trim ());
-            
-            m_settings = settings;
-            return settings;
-        }
-        
-        return settings;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private String m_verbosity;
-    private String m_verbosityFilter;
-    
-    private transient IProperties m_settings; // can be null
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/data/mergeTask.java b/ant/ant14/com/vladium/emma/data/mergeTask.java
deleted file mode 100644
index 361f3e9..0000000
--- a/ant/ant14/com/vladium/emma/data/mergeTask.java
+++ /dev/null
@@ -1,102 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: mergeTask.java,v 1.1.1.1.2.1 2004/07/08 10:52:09 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.File;
-
-import org.apache.tools.ant.BuildException;
-
-import com.vladium.emma.ant.FileTask;
-import com.vladium.emma.ant.SuppressableTask;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class mergeTask extends FileTask 
-{
-    // public: ................................................................
-    
-    
-    public mergeTask (final SuppressableTask parent)
-    {
-        super (parent);
-    }
-    
-    public void execute () throws BuildException
-    {
-        if (isEnabled ())
-        {
-            String [] files = getDataPath (true);
-            if ((files == null) || (files.length == 0))
-                throw (BuildException) newBuildException (getTaskName ()
-                    + ": no valid input data files have been specified", location).fillInStackTrace ();
-            
-            final MergeProcessor processor = MergeProcessor.create ();
-            
-            processor.setDataPath (files); files = null;
-            processor.setSessionOutFile (m_outFile != null ? m_outFile.getAbsolutePath () : null);
-            processor.setPropertyOverrides (getTaskSettings ());
-            
-            processor.run ();
-        }
-    }
-    
-
-    // mergefile|tofile|outfile|file attribute:
-    
-    public void setMergefile (final File file)
-    {
-        if (m_outFile != null)
-            throw (BuildException) newBuildException (getTaskName ()
-                + ": merge data file attribute already set", location).fillInStackTrace ();
-            
-        m_outFile = file;
-    }
-    
-    public void setOutfile (final File file)
-    {
-        if (m_outFile != null)
-            throw (BuildException) newBuildException (getTaskName ()
-                + ": merge data file attribute already set", location).fillInStackTrace ();
-            
-        m_outFile = file;
-    }
-
-    public void setTofile (final File file)
-    {
-        if (m_outFile != null)
-            throw (BuildException) newBuildException (getTaskName ()
-                + ": merge data file attribute already set", location).fillInStackTrace ();
-            
-        m_outFile = file;
-    }
-    
-    public void setFile (final File file)
-    {
-        if (m_outFile != null)
-            throw (BuildException) newBuildException (getTaskName ()
-                + ": merge data file attribute already set", location).fillInStackTrace ();
-            
-        m_outFile = file;
-    }
-    
-        
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private File m_outFile;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/emmaTask.java b/ant/ant14/com/vladium/emma/emmaTask.java
deleted file mode 100644
index 6aa726f..0000000
--- a/ant/ant14/com/vladium/emma/emmaTask.java
+++ /dev/null
@@ -1,117 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: emmaTask.java,v 1.1.1.1.2.2 2004/07/10 03:34:52 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import com.vladium.emma.IAppConstants;
-import java.util.ArrayList;
-import java.util.List;
-
-import org.apache.tools.ant.BuildException;
-import org.apache.tools.ant.Project;
-
-import com.vladium.emma.ant.NestedTask;
-import com.vladium.emma.ant.SuppressableTask;
-import com.vladium.emma.data.mergeTask;
-import com.vladium.emma.instr.instrTask;
-import com.vladium.emma.report.reportTask;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class emmaTask extends SuppressableTask
-{
-    // public: ................................................................
-    
-    // TODO: this and related tasks should be designed for external extensibility
-    // [make non final and use virtual prop getters]
-    
-    public emmaTask ()
-    {
-        m_tasks = new ArrayList ();
-    }
-    
-    
-    public synchronized void execute () throws BuildException
-    {
-        log (IAppConstants.APP_VERBOSE_BUILD_ID, Project.MSG_VERBOSE);
-        
-        if (isEnabled ())
-        {
-            while (! m_tasks.isEmpty ())
-            {
-                final NestedTask task = (NestedTask) m_tasks.remove (0);
-                
-                final String name = getTaskName ();
-                try
-                {
-                    setTaskName (task.getTaskName ());
-                    
-                    task.execute ();
-                }
-                finally
-                {
-                    setTaskName (name);
-                }
-            }
-        }
-    }
-
-    
-    public NestedTask createInstr ()
-    {
-        return addTask (new instrTask (this), getNestedTaskName ("instr"));
-    }
-    
-    public NestedTask createMerge ()
-    {
-        return addTask (new mergeTask (this), getNestedTaskName ("merge"));
-    }
-    
-    public NestedTask createReport ()
-    {
-        return addTask (new reportTask (this), getNestedTaskName ("report"));
-    }
-    
-    // protected: .............................................................
-
-
-    protected NestedTask addTask (final NestedTask task, final String pseudoName)
-    {
-        initTask (task, pseudoName);
-        
-        m_tasks.add (task);
-        return task;
-    }
-    
-    protected void initTask (final NestedTask task, final String pseudoName)
-    {
-        task.setTaskName (pseudoName);
-        task.setProject (getProject ());
-        task.setLocation (getLocation ());
-        task.setOwningTarget (getOwningTarget ());
-        
-        task.init ();
-    }
-    
-    protected String getNestedTaskName (final String subname)
-    {
-        return getTaskName ().concat (".").concat (subname);
-    }
-        
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private final List /* NestedTask */ m_tasks;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/emmajavaTask.java b/ant/ant14/com/vladium/emma/emmajavaTask.java
deleted file mode 100644
index cf4339a..0000000
--- a/ant/ant14/com/vladium/emma/emmajavaTask.java
+++ /dev/null
@@ -1,587 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: emmajavaTask.java,v 1.1.1.1.2.2 2004/07/16 23:32:04 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import java.io.File;
-
-import com.vladium.util.IProperties;
-import com.vladium.util.Strings;
-import com.vladium.emma.ant.*;
-import com.vladium.emma.instr.FilterCfg;
-import com.vladium.emma.instr.FilterCfg.filterElement;
-import com.vladium.emma.report.ReportCfg;
-import com.vladium.emma.report.IReportEnums.DepthAttribute;
-import com.vladium.emma.report.IReportEnums.UnitsTypeAttribute;
-import com.vladium.emma.report.ReportCfg.Element_HTML;
-import com.vladium.emma.report.ReportCfg.Element_TXT;
-import com.vladium.emma.report.ReportCfg.Element_XML;
-
-import org.apache.tools.ant.BuildException;
-import org.apache.tools.ant.Project;
-import org.apache.tools.ant.taskdefs.Java;
-import org.apache.tools.ant.types.Commandline;
-import org.apache.tools.ant.types.Path;
-import org.apache.tools.ant.types.Reference;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-class emmajavaTask extends Java
-{
-    // public: ................................................................
-    
-    
-    public void init () throws BuildException
-    {
-        super.init ();
-
-        m_verbosityCfg = new VerbosityCfg ();
-        m_genericCfg = new GenericCfg (this);
-        m_filterCfg = new FilterCfg (this);
-        m_reportCfg = new ReportCfg (project, this);
-        setEnabled (true);        
-    }
-
-    
-    public void execute () throws BuildException
-    {
-        log (IAppConstants.APP_VERBOSE_BUILD_ID, Project.MSG_VERBOSE);
-        
-        if (getClasspath () == null)
-            throw (BuildException) SuppressableTask.newBuildException (getTaskName ()
-                + ": this task requires 'classpath' attribute to be set", location).fillInStackTrace ();
-            
-
-        if (isEnabled ())
-        {
-            // fork:
-            if (m_forkUserOverride && ! m_fork)
-                log (getTaskName () + ": 'fork=\"false\"' attribute setting ignored (this task always forks)", Project.MSG_WARN);
-            
-            super.setFork (true); // always fork
-            
-            // add emma libs to the parent task's classpath [to support non-extdir deployment]:
-            final Path libClasspath = m_libClasspath;
-            if ((libClasspath != null) && (libClasspath.size () > 0))
-            {
-                super.createClasspath ().append (libClasspath);
-            }
-            
-            // classname|jar (1/2):
-            super.setClassname ("emmarun");
-            
-            // <emmajava> extensions:
-            {
-                // report types:
-                {
-                    String reportTypes = Strings.toListForm (m_reportCfg.getReportTypes (), ',');
-                    if ((reportTypes == null) || (reportTypes.length () == 0)) reportTypes = "txt";
-                    
-                    super.createArg ().setValue ("-r");
-                    super.createArg ().setValue (reportTypes);
-                }
-                
-                // full classpath scan flag:
-                {
-                    if (m_scanCoveragePath)
-                    {
-                        super.createArg ().setValue ("-f");
-                    }
-                }
-                
-                // dump raw data flag and options:
-                {
-                    if (m_dumpSessionData)
-                    {
-                        super.createArg ().setValue ("-raw");
-                        
-                        if (m_outFile != null)
-                        {
-                            super.createArg ().setValue ("-out");
-                            super.createArg ().setValue (m_outFile.getAbsolutePath ());
-                        }
-                        
-                        if (m_outFileMerge != null)
-                        {
-                            super.createArg ().setValue ("-merge");
-                            super.createArg ().setValue (m_outFileMerge.booleanValue () ? "y" : "n");
-                        }
-                    }
-                    else
-                    {
-                        if (m_outFile != null)
-                            log (getTaskName () + ": output file attribute ignored ('fullmetadata=\"true\"' not specified)", Project.MSG_WARN);
-                        
-                        if (m_outFileMerge != null)
-                            log (getTaskName () + ": merge attribute setting ignored ('fullmetadata=\"true\"' not specified)", Project.MSG_WARN);
-                    }
-                } 
-                
-                // instr filter:
-                {
-                    final String [] specs = m_filterCfg.getFilterSpecs ();
-                    if ((specs != null) && (specs.length > 0))
-                    {
-                        super.createArg ().setValue ("-ix");
-                        super.createArg ().setValue (Strings.toListForm (specs, ','));
-                    }
-                }
-                
-                // sourcepath:
-                {
-                    final Path srcpath = m_reportCfg.getSourcepath ();
-                    if (srcpath != null)
-                    {
-                        super.createArg ().setValue ("-sp");
-                        super.createArg ().setValue (Strings.toListForm (srcpath.list (), ','));
-                    }
-                }
-                
-                // all other generic settings:
-                {
-                    final IProperties reportSettings = m_reportCfg.getReportSettings ();
-                    final IProperties genericSettings = m_genericCfg.getGenericSettings ();
-                    
-                    // TODO: another options is to read this file in the forked JVM [use '-props' pass-through]
-                    // the best option depends on how ANT resolves relative file names 
-                    final IProperties fileSettings = m_genericCfg.getFileSettings ();
-                    
-                    // verbosity settings use dedicated attributes and hence are more specific
-                    // than anything generic:
-                    final IProperties verbositySettings = m_verbosityCfg.getSettings ();
-                    
-                    // (1) file settings have lower priority than any explicitly named overrides
-                    // (2) named report settings override generic named settings
-                    // (3) verbosity settings use dedicated attributes (not overlapping with report
-                    // cfg) and hence are more specific than anything generic
-                    final IProperties settings = IProperties.Factory.combine (reportSettings,
-                                                 IProperties.Factory.combine (verbositySettings,
-                                                 IProperties.Factory.combine (genericSettings,
-                                                                              fileSettings)));
-                    
-                    final String [] argForm = settings.toAppArgsForm ("-D");
-                    if (argForm.length > 0)
-                    {
-                        for (int a = 0; a < argForm.length; ++ a)
-                            super.createArg ().setValue (argForm [a]);
-                    }
-                }
-            }
-            
-            // [assertion: getClasspath() is not null]
-            
-            // classpath:
-            super.createArg ().setValue ("-cp");
-            super.createArg ().setPath (getClasspath ());
-                        
-            // classname|jar (2/2):
-            if (getClassname () != null)
-                super.createArg ().setValue (getClassname ());
-            else if (getJar () != null)
-            {
-                super.createArg ().setValue ("-jar");
-                super.createArg ().setValue (getJar ().getAbsolutePath ());
-            }
-            else
-                throw (BuildException) SuppressableTask.newBuildException (getTaskName ()
-                    + "either 'jar' or 'classname' attribute must be set", location).fillInStackTrace ();
-                
-            // main class args:
-            if (m_appArgs != null)
-            {
-                final String [] args = m_appArgs.getArguments ();
-                for (int a = 0; a < args.length; ++ a)
-                {
-                    super.createArg ().setValue (args [a]); // note: spaces etc are escaped correctly by ANT libs
-                }
-            }
-        }
-        else
-        {
-            // fork:
-            super.setFork (m_fork);
-            
-            // [assertion: getClasspath() is not null]
-            
-            // classpath:
-            super.createClasspath ().append (getClasspath ()); // can't use setClasspath() for obvious reasons
-            
-            // classname|jar:
-            if (getClassname () != null)
-                super.setClassname (getClassname ());
-            else if (getJar () != null)
-                super.setJar (getJar ());
-            else
-                throw (BuildException) SuppressableTask.newBuildException (getTaskName ()
-                    + "either 'jar' or 'classname' attribute must be set", location).fillInStackTrace ();
-            
-            // main class args:
-            if (m_appArgs != null)
-            {
-                final String [] args = m_appArgs.getArguments ();
-                for (int a = 0; a < args.length; ++ a)
-                {
-                    super.createArg ().setValue (args [a]); // note: spaces etc are escaped correctly by ANT libs
-                }
-            }    
-        }
-        
-        super.execute ();
-    }
-
-    
-    
-    // <java> overrides [ANT 1.4]:
-    
-    public void setClassname (final String classname)
-    {
-        if (getJar () != null)
-            throw (BuildException) SuppressableTask.newBuildException (getTaskName ()
-                + "'jar' and 'classname' attributes cannot be set at the same time", location).fillInStackTrace ();
-            
-        m_classname = classname;
-    }
-    
-    public void setJar (final File file)
-    {
-        if (getClassname () != null)
-            throw (BuildException) SuppressableTask.newBuildException (getTaskName ()
-                + "'jar' and 'classname' attributes cannot be set at the same time", location).fillInStackTrace ();
-            
-        m_jar = file;
-    }
-    
-    
-    public void setClasspath (final Path path)
-    {
-        if (m_classpath == null)
-            m_classpath = path;
-        else
-            m_classpath.append (path);
-    }
-    
-    public void setClasspathRef (final Reference ref)
-    {
-        createClasspath ().setRefid (ref);
-    }
-    
-    public Path createClasspath ()
-    {
-        if (m_classpath == null)
-            m_classpath = new Path (project);
-        
-        return m_classpath.createPath ();
-    }
-    
-    /**
-     * This is already deprecated in ANT v1.4. However, it is still supported by
-     * the parent task so I do likewise.
-     */ 
-    public void setArgs (final String args)
-    {
-        throw (BuildException) SuppressableTask.newBuildException (getTaskName ()
-            + ": disallows using <java>'s deprecated 'args' attribute", location).fillInStackTrace ();
-    }
-
-    /**
-     * Not overridable.
-     */
-    public final void setFork (final boolean fork)
-    {
-        m_fork = fork;
-        m_forkUserOverride = true;
-    }
-    
-    /**
-     * Not overridable [due to limitations in ANT's Commandline].
-     */
-    public final Commandline.Argument createArg ()
-    {
-        if (m_appArgs == null)
-            m_appArgs = new Commandline ();
-        
-        return m_appArgs.createArgument ();
-    }
-    
-    // <java> overrides [ANT 1.5]:
-    
-    // [nothing at this point]
-    
-    
-    // <emmajava> extensions:
-    
-    public void setEnabled (final boolean enabled)
-    {
-        m_enabled = enabled;
-    }
-    
-    // .properties file attribute:
-    
-    public final void setProperties (final File file)
-    {
-        m_genericCfg.setProperties (file);
-    }
-
-    // generic property element:
-    
-    public final PropertyElement createProperty ()
-    {
-        return m_genericCfg.createProperty ();
-    }
-    
-    // verbosity attribute:
-    
-    public void setVerbosity (final VerbosityCfg.VerbosityAttribute verbosity)
-    {
-        m_verbosityCfg.setVerbosity (verbosity);
-    }
-    
-    // verbosity class filter attribute:
-    
-    public void setVerbosityfilter (final String filter)
-    {
-        m_verbosityCfg.setVerbosityfilter (filter);
-    }
-    
-    // lib classpath attribute [to support non-extdir deployment]:
-    
-    public final void setLibclasspath (final Path classpath)
-    {
-        if (m_libClasspath == null)
-            m_libClasspath = classpath;
-        else
-            m_libClasspath.append (classpath);
-    }
-    
-    public final void setLibclasspathRef (final Reference ref)
-    {
-        if (m_libClasspath == null)
-            m_libClasspath = new Path (project);
-        
-        m_libClasspath.createPath ().setRefid (ref);
-    }
-    
-    // -f flag:
-    
-    public void setFullmetadata (final boolean full)
-    {
-        m_scanCoveragePath = full; // defaults to false TODO: maintain the default in a central location
-    }
-    
-    // -raw flag:
-    
-    public void setDumpsessiondata (final boolean dump)
-    {
-        m_dumpSessionData = dump;
-    }
-    
-    // -out option:
-    
-    // sessiondatafile|outfile attribute:
-    
-    public void setSessiondatafile (final File file)
-    {
-        if (m_outFile != null)
-            throw (BuildException) SuppressableTask.newBuildException (getTaskName ()
-                + ": session data file attribute already set", location).fillInStackTrace ();
-            
-        m_outFile = file;
-    }
-    
-    public void setOutfile (final File file)
-    {
-        if (m_outFile != null)
-            throw (BuildException) SuppressableTask.newBuildException (getTaskName ()
-                + ": session data file attribute already set", location).fillInStackTrace ();
-            
-        m_outFile = file;
-    }
-
-//    public void setTofile (final File file)
-//    {
-//        if (m_outFile != null)
-//            throw (BuildException) SuppressableTask.newBuildException (getTaskName ()
-//                + ": session data file attribute already set", location).fillInStackTrace ();
-//            
-//        m_outFile = file;
-//    }
-//    
-//    public void setFile (final File file)
-//    {
-//        if (m_outFile != null)
-//            throw (BuildException) SuppressableTask.newBuildException (getTaskName ()
-//                + ": session data file attribute already set", location).fillInStackTrace ();
-//            
-//        m_outFile = file;
-//    }
-    
-    
-    // merge attribute:
-     
-    public void setMerge (final boolean merge)
-    {
-        m_outFileMerge = merge ? Boolean.TRUE : Boolean.FALSE;       
-    }
-    
-    // instr filter attribute/element:
-    
-    public final void setFilter (final String filter)
-    {
-        m_filterCfg.setFilter (filter);
-    }
-    
-    public final filterElement createFilter ()
-    {
-        return m_filterCfg.createFilter ();
-    }
-
-    
-    // TODO: should what's below go inside <report></report> ?
-    
-    // sourcepath attribute/element:
-    
-    public final void setSourcepath (final Path path)
-    {
-        m_reportCfg.setSourcepath (path);
-    }
-    
-    public final void setSourcepathRef (final Reference ref)
-    {
-        m_reportCfg.setSourcepathRef (ref);
-    }
-    
-    public final Path createSourcepath ()
-    {
-        return m_reportCfg.createSourcepath ();
-    }
-    
-    
-    // generator elements:
-    
-    public final Element_TXT createTxt ()
-    {
-        return m_reportCfg.createTxt ();
-    }
-    
-    public final Element_HTML createHtml ()
-    {
-        return m_reportCfg.createHtml ();
-    }
-    
-    public final Element_XML createXml ()
-    {
-        return m_reportCfg.createXml ();
-    }
-    
-    
-    // report properties [defaults for all report types]:
-
-    public final void setUnits (final UnitsTypeAttribute units)
-    {
-        m_reportCfg.setUnits (units);
-    }    
-
-    public final void setDepth (final DepthAttribute depth)
-    {
-        m_reportCfg.setDepth (depth);
-    }
-    
-    public final void setColumns (final String columns)
-    {
-        m_reportCfg.setColumns (columns);
-    }
-    
-    public final void setSort (final String sort)
-    {
-        m_reportCfg.setSort (sort);
-    }
-    
-    public final void setMetrics (final String metrics)
-    {
-        m_reportCfg.setMetrics (metrics);
-    }
-    
-    // these are not supported anymore
-    
-//    public final void setOutdir (final File dir)
-//    {
-//        m_reportCfg.setOutdir (dir);
-//    }
-//    
-//    public final void setDestdir (final File dir)
-//    {
-//        m_reportCfg.setDestdir (dir);
-//    }
-
-      // should be set at this level [and conflicts with raw data opts]:
-          
-//    public void setOutfile (final String fileName)
-//    {
-//        m_reportCfg.setOutfile (fileName);
-//    }
-    
-    public void setEncoding (final String encoding)
-    {
-        m_reportCfg.setEncoding (encoding);
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected String getClassname ()
-    {
-        return m_classname;
-    }
-    
-    protected File getJar ()
-    {
-        return m_jar;
-    }
-    
-    protected Path getClasspath ()
-    {
-        return m_classpath;
-    }
-    
-    // extended functionality:
-    
-    protected boolean isEnabled ()
-    {
-        return m_enabled;
-    }
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    // <java> overrides:
-    
-    private Path m_classpath;
-    private String m_classname;
-    private File m_jar;
-    private Commandline m_appArgs;
-    private boolean m_fork, m_forkUserOverride;
-    
-    // <emmajava> extensions:
-    
-    private boolean m_enabled;
-    private Path m_libClasspath;
-    private /*final*/ VerbosityCfg m_verbosityCfg;
-    private /*final*/ GenericCfg m_genericCfg;
-    private /*final*/ FilterCfg m_filterCfg;
-    private /*final*/ ReportCfg m_reportCfg;
-    private boolean m_scanCoveragePath; // defaults to false 
-    private boolean m_dumpSessionData; //defaults to false
-    private File m_outFile;
-    private Boolean m_outFileMerge;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/instr/FilterCfg.java b/ant/ant14/com/vladium/emma/instr/FilterCfg.java
deleted file mode 100644
index 1d13cae..0000000
--- a/ant/ant14/com/vladium/emma/instr/FilterCfg.java
+++ /dev/null
@@ -1,195 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: FilterCfg.java,v 1.2 2004/05/20 02:28:07 vlad_r Exp $
- */
-package com.vladium.emma.instr;
-
-import java.io.File;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-
-import org.apache.tools.ant.BuildException;
-import org.apache.tools.ant.Task;
-
-import com.vladium.util.IConstants;
-import com.vladium.util.Strings;
-import com.vladium.emma.ant.StringValue;
-import com.vladium.emma.ant.SuppressableTask;
-import com.vladium.emma.filter.IInclExclFilter;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-class FilterCfg
-{
-    // public: ................................................................
-    
-    
-    public static final class filterElement extends StringValue
-    {
-        public filterElement (final Task task)
-        {
-            super (task);
-        }
-        
-        public void setValue (final String value)
-        {
-            final String [] specs = Strings.merge (new String [] {value}, COMMA_DELIMITERS, true);
-            
-            for (int i = 0; i < specs.length; ++ i)
-            {
-                final String spec = specs [i];
-                
-                if (spec.startsWith (IInclExclFilter.INCLUSION_PREFIX_STRING) ||
-                    spec.startsWith (IInclExclFilter.EXCLUSION_PREFIX_STRING))
-                {
-                    appendValue (spec, COMMA);
-                }
-                else
-                {
-                    appendValue (IInclExclFilter.INCLUSION_PREFIX + spec, COMMA); // default to inclusion
-                }
-            }
-        }
-        
-        /**
-         * Set the 'file' attribute.
-         */
-        public void setFile (final File file)
-        {
-            appendValue ("@".concat (file.getAbsolutePath ()), COMMA); // actual file I/O delayed until getFilterSpecs()
-        }
-        
-        public void setIncludes (final String value)
-        {
-            final String [] specs = Strings.merge (new String [] {value}, COMMA_DELIMITERS, true);
-            
-            for (int i = 0; i < specs.length; ++ i)
-            {
-                final String spec = specs [i];
-                
-                if (spec.startsWith (IInclExclFilter.INCLUSION_PREFIX_STRING))
-                {
-                    appendValue (spec, COMMA);
-                }
-                else
-                {
-                    if (spec.startsWith (IInclExclFilter.EXCLUSION_PREFIX_STRING))
-                        appendValue (IInclExclFilter.INCLUSION_PREFIX + spec.substring (1), COMMA); // override
-                    else
-                        appendValue (IInclExclFilter.INCLUSION_PREFIX + spec, COMMA);
-                }
-            }
-        }
-        
-        public void setExcludes (final String value)
-        {
-            final String [] specs = Strings.merge (new String [] {value}, COMMA_DELIMITERS, true);
-            
-            for (int i = 0; i < specs.length; ++ i)
-            {
-                final String spec = specs [i];
-                
-                if (spec.startsWith (IInclExclFilter.EXCLUSION_PREFIX_STRING))
-                {
-                    appendValue (spec, COMMA);
-                }
-                else
-                {
-                    if (spec.startsWith (IInclExclFilter.INCLUSION_PREFIX_STRING))
-                        appendValue (IInclExclFilter.EXCLUSION_PREFIX + spec.substring (1), COMMA); // override
-                    else
-                        appendValue (IInclExclFilter.EXCLUSION_PREFIX + spec, COMMA);
-                }
-            }
-        }
-        
-    } // end of nested class
-    
-
-    public FilterCfg (final Task task)
-    {
-        if (task == null) throw new IllegalArgumentException ("null input: task");
-        
-        m_task = task;
-        m_filterList = new ArrayList ();
-    }
-
-    
-    // filter attribute/element:
-    
-    public void setFilter (final String filter)
-    {
-        createFilter ().appendValue (filter, COMMA);
-    }
-    
-    public filterElement createFilter ()
-    {
-        final filterElement result = new filterElement (m_task);
-        m_filterList.add (result);
-        
-        return result;
-    }
-    
-    // ACCESSORS:
-
-    public String [] getFilterSpecs ()
-    {
-        if (m_specs != null)
-            return m_specs;
-        else
-        {           
-            if ((m_filterList == null) || m_filterList.isEmpty ())
-            {
-                m_specs = IConstants.EMPTY_STRING_ARRAY;
-            }
-            else
-            {
-                final String [] values = new String [m_filterList.size ()];
-                
-                int j = 0;
-                for (Iterator i = m_filterList.iterator (); i.hasNext (); ++ j)
-                    values [j] = ((StringValue) i.next ()).getValue ();
-                                
-                try
-                {
-                    m_specs = Strings.mergeAT (values, COMMA_DELIMITERS, true);
-                }
-                catch (IOException ioe)
-                {
-                    throw (BuildException) SuppressableTask.newBuildException (m_task.getTaskName ()
-                        + ": I/O exception while processing input" , ioe, m_task.getLocation ()).fillInStackTrace ();
-                }
-            }
-            
-            return m_specs;
-        }
-    }
-    
-    // protected: .............................................................
-
-
-    protected static final String COMMA               = ",";
-    protected static final String COMMA_DELIMITERS    = COMMA + Strings.WHITE_SPACE;
-    protected static final String PATH_DELIMITERS     = COMMA.concat (File.pathSeparator);
-    
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-    
-    private final Task m_task; // never null
-    private final List /* filterElement */ m_filterList; // never null
-    
-    private transient String [] m_specs;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/instr/instrTask.java b/ant/ant14/com/vladium/emma/instr/instrTask.java
deleted file mode 100644
index 30c9f3d..0000000
--- a/ant/ant14/com/vladium/emma/instr/instrTask.java
+++ /dev/null
@@ -1,181 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: instrTask.java,v 1.1.1.1.2.1 2004/07/08 10:52:12 vlad_r Exp $
- */
-package com.vladium.emma.instr;
-
-import java.io.File;
-
-import org.apache.tools.ant.BuildException;
-import org.apache.tools.ant.types.EnumeratedAttribute;
-import org.apache.tools.ant.types.Path;
-import org.apache.tools.ant.types.Reference;
-
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.ant.FilterTask;
-import com.vladium.emma.ant.SuppressableTask;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class instrTask extends FilterTask
-{
-    // public: ................................................................
-
-
-    public static final class ModeAttribute extends EnumeratedAttribute
-    {
-        public String [] getValues ()
-        {
-            return VALUES;
-        }
-        
-        private static final String [] VALUES = new String [] {"copy", "overwrite", "fullcopy"};
-
-    } // end of nested class
-    
-    
-    public instrTask (final SuppressableTask parent)
-    {
-        super (parent);
-        
-        m_outMode = InstrProcessor.OutMode.OUT_MODE_COPY; // default
-    }
-    
-        
-    public void execute () throws BuildException
-    {
-        if (isEnabled ())
-        {
-            if (m_instrpath == null)
-                throw (BuildException) newBuildException (getTaskName ()
-                    + ": instrumentation path must be specified", location).fillInStackTrace ();
- 
-            if ((m_outMode != InstrProcessor.OutMode.OUT_MODE_OVERWRITE) && (m_outDir == null))
-                throw (BuildException) newBuildException (getTaskName ()
-                    + ": output directory must be specified for '" + m_outMode + "' output mode", location).fillInStackTrace ();
-            
-            InstrProcessor processor = InstrProcessor.create ();
-                
-            $assert.ASSERT (m_instrpath != null, "m_instrpath not set");
-            processor.setInstrPath (m_instrpath.list (), true); // TODO: an option to set 'canonical'?
-            // processor.setDependsMode ()
-            processor.setInclExclFilter (getFilterSpecs ());
-            $assert.ASSERT (m_outMode != null, "m_outMode not set");
-            processor.setOutMode (m_outMode);
-            processor.setInstrOutDir (m_outDir != null ? m_outDir.getAbsolutePath () : null);
-            processor.setMetaOutFile (m_outFile != null ? m_outFile.getAbsolutePath () : null);
-            processor.setMetaOutMerge (m_outFileMerge);
-            processor.setPropertyOverrides (getTaskSettings ());
-            
-            processor.run ();
-        }
-    }
-    
-       
-    // instrpath attribute/element:
-    
-    public void setInstrpath (final Path path)
-    {
-        if (m_instrpath == null)
-            m_instrpath = path;
-        else
-            m_instrpath.append (path);
-    }
-    
-    public void setInstrpathRef (final Reference ref)
-    {
-        createInstrpath ().setRefid (ref);
-    }
-    
-    public Path createInstrpath ()
-    {
-        if (m_instrpath == null)
-            m_instrpath = new Path (project);
-        
-        return m_instrpath.createPath ();
-    }
-    
-    
-    // outdir|destdir attribute:
-    
-    public void setOutdir (final File dir)
-    {
-        if (m_outDir != null)
-            throw (BuildException) newBuildException (getTaskName ()
-                + ": outdir|destdir attribute already set", location).fillInStackTrace ();
-            
-        m_outDir = dir;
-    }
-    
-    public void setDestdir (final File dir)
-    {
-        if (m_outDir != null)
-            throw (BuildException) newBuildException (getTaskName ()
-                + ": outdir|destdir attribute already set", location).fillInStackTrace ();
-        
-        m_outDir = dir;
-    }
-    
-
-    // metadatafile|outfile attribute:
-
-    public void setMetadatafile (final File file)
-    {
-        if (m_outFile != null)
-            throw (BuildException) newBuildException (getTaskName ()
-                + ": metadata file attribute already set", location).fillInStackTrace ();
-            
-        m_outFile = file;
-    }
-    
-    public void setOutfile (final File file)
-    {
-        if (m_outFile != null)
-            throw (BuildException) newBuildException (getTaskName ()
-                + ": metadata file attribute already set", location).fillInStackTrace ();
-            
-        m_outFile = file;
-    }
-    
-    // merge attribute:
-     
-    public void setMerge (final boolean merge)
-    {
-        m_outFileMerge = merge ? Boolean.TRUE : Boolean.FALSE;       
-    }
-    
-    
-    // mode attribute:
-    
-    public void setMode (final ModeAttribute mode)
-    {        
-        final InstrProcessor.OutMode outMode = InstrProcessor.OutMode.nameToMode (mode.getValue ());
-        if (outMode == null)
-            throw (BuildException) newBuildException (getTaskName ()
-                + ": invalid output mode: " + mode.getValue (), location).fillInStackTrace ();
-        
-        m_outMode = outMode;
-    }
-    
-    // protected: .............................................................
-        
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-        
-    private Path m_instrpath;
-    private InstrProcessor.OutMode m_outMode;
-    private File m_outDir;
-    private File m_outFile;
-    private Boolean m_outFileMerge;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/report/IReportEnums.java b/ant/ant14/com/vladium/emma/report/IReportEnums.java
deleted file mode 100644
index 7b81457..0000000
--- a/ant/ant14/com/vladium/emma/report/IReportEnums.java
+++ /dev/null
@@ -1,96 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IReportEnums.java,v 1.1.1.1 2004/05/09 16:57:27 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import com.vladium.emma.report.IReportProperties;
-import org.apache.tools.ant.types.EnumeratedAttribute;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IReportEnums
-{
-    // public: ................................................................
-
-
-    final class TypeAttribute extends EnumeratedAttribute
-    {
-        public String [] getValues ()
-        {
-            return VALUES;
-        }
-        
-        // TODO: keep this enum in a centralized location
-        private static final String [] VALUES = new String []
-        {
-            "txt",
-            "html",
-            "xml",
-        };
-
-    } // end of nested class
-    
-
-    final class DepthAttribute extends EnumeratedAttribute
-    {
-        public String [] getValues ()
-        {
-            return VALUES;
-        }
-        
-        // TODO: keep this enum in a centralized location
-        private static final String [] VALUES = new String []
-        {
-            IReportProperties.DEPTH_ALL,
-            IReportProperties.DEPTH_PACKAGE,
-            IReportProperties.DEPTH_SRCFILE,
-            IReportProperties.DEPTH_CLASS,
-            IReportProperties.DEPTH_METHOD,
-        };
-
-    } // end of nested class
-    
-
-    final class ViewTypeAttribute extends EnumeratedAttribute
-    {
-        public String [] getValues ()
-        {
-            return VALUES;
-        }
-        
-        // TODO: keep this enum in a centralized location
-        private static final String [] VALUES = new String []
-        {
-            IReportProperties.SRC_VIEW,
-            IReportProperties.CLS_VIEW,
-        };
-
-    } // end of nested class
-    
-    
-    static final class UnitsTypeAttribute extends EnumeratedAttribute
-    {
-        public String [] getValues ()
-        {
-            return VALUES;
-        }
-        
-        // TODO: keep this enum in a centralized location
-        private static final String [] VALUES = new String []
-        {
-            IReportProperties.INSTR_UNITS,
-            IReportProperties.COUNT_UNITS,
-        };
-
-    } // end of nested class
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/report/ReportCfg.java b/ant/ant14/com/vladium/emma/report/ReportCfg.java
deleted file mode 100644
index 71a01b4..0000000
--- a/ant/ant14/com/vladium/emma/report/ReportCfg.java
+++ /dev/null
@@ -1,424 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ReportCfg.java,v 1.1.1.1.2.1 2004/07/08 10:52:11 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Properties;
-
-import com.vladium.util.IConstants;
-import com.vladium.util.IProperties;
-import com.vladium.emma.EMMAProperties;
-import com.vladium.emma.ant.PropertyElement;
-import com.vladium.emma.ant.SuppressableTask;
-import com.vladium.emma.report.IReportEnums.DepthAttribute;
-import com.vladium.emma.report.IReportEnums.UnitsTypeAttribute;
-
-import org.apache.tools.ant.BuildException;
-import org.apache.tools.ant.Project;
-import org.apache.tools.ant.Task;
-import org.apache.tools.ant.types.Path;
-import org.apache.tools.ant.types.Reference;
-
-// ----------------------------------------------------------------------------
-/**
- * ReportCfg is a container for report type {@link ReportCfg.Element}s that are
- * in turn containers for all properties that could be set on a &lt;report&gt;
- * report type configurator (&lt;txt&gt;, &lt;html&gt;, etc). The elements provide
- * the ability for report properties to be set either via the generic &lt;property&gt;
- * nested elements or dedicated attributes. Potential conflicts between the same
- * conceptual property being set via an attribute and a nested element are resolved
- * by making dedicated attributes higher priority.<P>
- * 
- * Note that ReportCfg does not handle any non-report related properties.
- * This can be done via {@link com.vladium.emma.ant.GenericCfg}. It is also the
- * parent's responsibility to merge any inherited report properties with
- * ReportCfg settings. 
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-class ReportCfg implements IReportProperties
-{
-    // public: ................................................................
-
-
-    public static abstract class Element implements IReportEnums, IReportProperties
-    {
-        public void setUnits (final UnitsTypeAttribute units)
-        {
-            m_settings.setProperty (m_prefix.concat (UNITS_TYPE), units.getValue ());
-        }
-        
-        public void setDepth (final DepthAttribute depth)
-        {
-            m_settings.setProperty (m_prefix.concat (DEPTH), depth.getValue ());
-        }
-        
-        public void setColumns (final String columns)
-        {
-            m_settings.setProperty (m_prefix.concat (COLUMNS), columns);
-        }
-        
-        public void setSort (final String sort)
-        {
-            m_settings.setProperty (m_prefix.concat (SORT), sort);
-        }
-        
-        public void setMetrics (final String metrics)
-        {
-            m_settings.setProperty (m_prefix.concat (METRICS), metrics);
-        }
-        
-        // not supported anymore:
-        
-//        public void setOutdir (final File dir)
-//        {
-//            // TODO: does ANT resolve files relative to current JVM dir or ${basedir}?
-//            m_settings.setProperty (m_prefix.concat (OUT_DIR), dir.getAbsolutePath ());
-//        }
-        
-        public void setOutfile (final String fileName)
-        {
-            m_settings.setProperty (m_prefix.concat (OUT_FILE), fileName);
-        }
-        
-        public void setEncoding (final String encoding)
-        {
-            m_settings.setProperty (m_prefix.concat (OUT_ENCODING), encoding);
-        }
-        
-        // generic property element [don't doc this publicly]:
-        
-        public PropertyElement createProperty ()
-        {
-            // TODO: error out on conficting duplicate settings
-            
-            final PropertyElement property = new PropertyElement ();
-            m_genericSettings.add (property);
-            
-            return property;
-        }
-        
-        protected abstract String getType ();
-        
-
-        Element (final Task task, final IProperties settings)
-        {
-            if (task == null)
-                throw new IllegalArgumentException ("null input: task");
-            if (settings == null)
-                throw new IllegalArgumentException ("null input: settings");
-            
-            m_task = task;
-            m_settings = settings;
-            
-            m_prefix = PREFIX.concat (getType ()).concat (".");
-            
-            m_genericSettings = new ArrayList ();
-        }
-        
-        
-        void processGenericSettings ()
-        {
-            for (Iterator i = m_genericSettings.iterator (); i.hasNext (); )
-            {
-                final PropertyElement property = (PropertyElement) i.next ();
-                
-                final String name = property.getName ();
-                final String value = property.getValue () != null ? property.getValue () : "";
-                
-                if (name != null)
-                {
-                    final String prefixedName = m_prefix.concat (name);
-                    
-                    // generically named settings don't override report named settings:
-                    
-                    if (! m_settings.isOverridden (prefixedName))
-                        m_settings.setProperty (prefixedName, value);
-                }
-            }
-        }
-        
-        
-        protected final Task m_task; // never null
-        protected final String m_prefix; // never null
-        protected final IProperties m_settings; // never null
-        protected final List /* PropertyElement */ m_genericSettings; // never null
-        
-    } // end of nested class
-
-    // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-
-    public static class Element_HTML extends Element
-    {
-        protected final String getType ()
-        {
-            return TYPE;
-        }
-        
-        Element_HTML (final Task task, final IProperties settings)
-        {
-            super (task, settings);
-        }
-        
-        
-        static final String TYPE = "html";
-        
-    } // end of nested class
-    
-    // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-    
-    public static class Element_TXT extends Element
-    {
-        protected final String getType ()
-        {
-            return TYPE;
-        }
-        
-        Element_TXT (final Task task, final IProperties settings)
-        {
-            super (task, settings);
-        }
-        
-        
-        static final String TYPE = "txt";
-        
-    } // end of nested class
-    
-    // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-    
-    public static class Element_XML extends Element
-    {
-        protected final String getType ()
-        {
-            return TYPE;
-        }
-        
-        Element_XML (final Task task, final IProperties settings)
-        {
-            super (task, settings);
-        }
-        
-        
-        static final String TYPE = "xml";
-        
-    } // end of nested class
-    
-    // ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-    
-    
-    public ReportCfg (final Project project, final Task task)
-    {
-        m_project = project;
-        m_task = task;
-        
-        m_reportTypes = new ArrayList (4);
-        m_cfgList = new ArrayList (4);
-        m_settings = EMMAProperties.wrap (new Properties ());
-    }
-    
-    public Path getSourcepath ()
-    {
-        return m_srcpath;
-    }
-    
-    public String [] getReportTypes ()
-    {
-        final BuildException failure = getFailure ();
-        
-        if (failure != null)
-            throw failure;
-        else
-        {
-            if (m_reportTypes.isEmpty ())
-                return IConstants.EMPTY_STRING_ARRAY;
-            else
-            {
-                final String [] result = new String [m_reportTypes.size ()];
-                m_reportTypes.toArray (result);
-                
-                return result;
-            }
-        }
-    }
-    
-    public IProperties getReportSettings ()
-    {
-        final BuildException failure = getFailure ();
-        
-        if (failure != null)
-            throw failure;
-        else
-        {
-            if (! m_processed)
-            {
-                // collect all nested elements' generic settins into m_settings:
-                
-                for (Iterator i = m_cfgList.iterator (); i.hasNext (); )
-                {
-                    final Element cfg = (Element) i.next ();
-                    cfg.processGenericSettings ();
-                }
-                
-                m_processed = true;
-            }
-            
-            return m_settings; // no clone
-        }
-    }
-    
-    
-    // sourcepath attribute/element:
-    
-    public void setSourcepath (final Path path)
-    {
-        if (m_srcpath == null)
-            m_srcpath = path;
-        else
-            m_srcpath.append (path);
-    }
-    
-    public void setSourcepathRef (final Reference ref)
-    {
-        createSourcepath ().setRefid (ref);
-    }
-    
-    public Path createSourcepath ()
-    {
-        if (m_srcpath == null)
-            m_srcpath = new Path (m_project);
-        
-        return m_srcpath.createPath ();
-    }
-    
-    
-    // generator elements:
-    
-    public Element_TXT createTxt ()
-    {
-        return (Element_TXT) addCfgElement (Element_TXT.TYPE,
-                                                     new Element_TXT (m_task, m_settings));
-    }
-    
-    public Element_HTML createHtml ()
-    {
-        return (Element_HTML) addCfgElement (Element_HTML.TYPE,
-                                                      new Element_HTML (m_task, m_settings));
-    }
-    
-    public Element_XML createXml ()
-    {
-        return (Element_XML) addCfgElement (Element_XML.TYPE,
-                                                     new Element_XML (m_task, m_settings));
-    }
-    
-    
-    // report properties [defaults for all report types]:
-
-    public void setUnits (final UnitsTypeAttribute units)
-    {
-        m_settings.setProperty (PREFIX.concat (UNITS_TYPE), units.getValue ());
-    }    
-
-    public void setDepth (final DepthAttribute depth)
-    {
-        m_settings.setProperty (PREFIX.concat (DEPTH), depth.getValue ());
-    }
-    
-    public void setColumns (final String columns)
-    {
-        m_settings.setProperty (PREFIX.concat (COLUMNS), columns);
-    }
-    
-    public void setSort (final String sort)
-    {
-        m_settings.setProperty (PREFIX.concat (SORT), sort);
-    }
-    
-    public void setMetrics (final String metrics)
-    {
-        m_settings.setProperty (PREFIX.concat (METRICS), metrics);
-    }
-
-    // not supported anymore:
-    
-//    public void setOutdir (final File dir)
-//    {
-//        // TODO: does ANT resolve files relative to current JVM dir or ${basedir}?
-//        m_settings.setProperty (PREFIX.concat (OUT_DIR), dir.getAbsolutePath ());
-//    }
-//    
-//    public void setDestdir (final File dir)
-//    {
-//        // TODO: does ANT resolve files relative to current JVM dir or ${basedir}?
-//        m_settings.setProperty (PREFIX.concat (OUT_DIR), dir.getAbsolutePath ());
-//    }
-    
-    public void setOutfile (final String fileName)
-    {
-        m_settings.setProperty (PREFIX.concat (OUT_FILE), fileName);
-    }
-    
-    public void setEncoding (final String encoding)
-    {
-        m_settings.setProperty (PREFIX.concat (OUT_ENCODING), encoding);
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected Element addCfgElement (final String type, final Element cfg)
-    {
-        if (m_reportTypes.contains (type))
-        {
-            setFailure ((BuildException) SuppressableTask.newBuildException (m_task.getTaskName ()
-                + ": duplicate configuration for report type [" + type + "]" ,
-                m_task.getLocation ()).fillInStackTrace ());
-        }
-        else
-        {
-            m_reportTypes.add (type);
-            m_cfgList.add (cfg);
-        }
-        
-        return cfg;
-    }
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private void setFailure (final BuildException failure)
-    {
-        if (m_settingsFailure == null) m_settingsFailure = failure; // record the first one only
-    }
-    
-    private BuildException getFailure ()
-    {
-        return m_settingsFailure;
-    }
-    
-    
-    private final Project m_project;
-    private final Task m_task;
-    
-    private final List /* report type:String */ m_reportTypes; // using a list to keep the generation order same as configuration
-    private final List /* Element */ m_cfgList;
-    private final IProperties m_settings; // never null
-    
-    private Path m_srcpath;
-    
-    private transient BuildException m_settingsFailure; // can be null
-    private transient boolean m_processed;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant14/com/vladium/emma/report/reportTask.java b/ant/ant14/com/vladium/emma/report/reportTask.java
deleted file mode 100644
index b726753..0000000
--- a/ant/ant14/com/vladium/emma/report/reportTask.java
+++ /dev/null
@@ -1,179 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: reportTask.java,v 1.1.1.1.2.1 2004/07/08 10:52:11 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import org.apache.tools.ant.BuildException;
-import org.apache.tools.ant.types.Path;
-import org.apache.tools.ant.types.Reference;
-
-import com.vladium.util.IProperties;
-import com.vladium.emma.ant.FileTask;
-import com.vladium.emma.ant.SuppressableTask;
-import com.vladium.emma.report.ReportCfg.Element_HTML;
-import com.vladium.emma.report.ReportCfg.Element_TXT;
-import com.vladium.emma.report.ReportCfg.Element_XML;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class reportTask extends FileTask implements IReportProperties, IReportEnums
-{
-    public reportTask (final SuppressableTask parent)
-    {
-        super (parent);
-    }
-    
-    public void init () throws BuildException
-    {
-        super.init ();
-        
-        m_reportCfg = new ReportCfg (getProject (), this);
-    }
-
-    
-    public void execute () throws BuildException
-    {
-        if (isEnabled ())
-        {
-            final String [] reportTypes = m_reportCfg.getReportTypes ();
-            
-            if ((reportTypes == null) || (reportTypes.length == 0)) // no "txt" default for report processor
-                throw (BuildException) newBuildException (getTaskName ()
-                    + ": no report types specified: provide at least one of <txt>, <html>, <xml> nested elements", location).fillInStackTrace ();
-
-            String [] files = getDataPath (true);
-            if ((files == null) || (files.length == 0))
-                throw (BuildException) newBuildException (getTaskName ()
-                    + ": no valid input data files have been specified", location).fillInStackTrace ();
-
-            final Path srcpath = m_reportCfg.getSourcepath ();
-            
-            // combine report and all generic settings:
-            final IProperties settings; 
-            {
-                final IProperties taskSettings = getTaskSettings ();
-                final IProperties reportSettings = m_reportCfg.getReportSettings ();
-                
-                // named report settings override generic named settings and file
-                // settings have lower priority than any explicitly named overrides:
-                settings = IProperties.Factory.combine (reportSettings, taskSettings);
-            }
-
-            final ReportProcessor processor = ReportProcessor.create ();
-            
-            processor.setDataPath (files); files = null;
-            processor.setSourcePath (srcpath != null ? srcpath.list () : null);
-            processor.setReportTypes (reportTypes);
-            processor.setPropertyOverrides (settings);        
-            
-            processor.run ();
-        }
-    }
-
-    
-    // sourcepath attribute/element:
-    
-    public void setSourcepath (final Path path)
-    {
-        m_reportCfg.setSourcepath (path);
-    }
-    
-    public void setSourcepathRef (final Reference ref)
-    {
-        m_reportCfg.setSourcepathRef (ref);
-    }
-    
-    public Path createSourcepath ()
-    {
-        return m_reportCfg.createSourcepath ();
-    }
-    
-    
-    // generator elements:
-    
-    public Element_TXT createTxt ()
-    {
-        return m_reportCfg.createTxt ();
-    }
-    
-    public Element_HTML createHtml ()
-    {
-        return m_reportCfg.createHtml ();
-    }
-    
-    public Element_XML createXml ()
-    {
-        return m_reportCfg.createXml ();
-    }
-    
-    
-    // report properties [defaults for all report types]:
-
-    public void setUnits (final UnitsTypeAttribute units)
-    {
-        m_reportCfg.setUnits (units);
-    }    
-
-    public void setDepth (final DepthAttribute depth)
-    {
-        m_reportCfg.setDepth (depth);
-    }
-    
-    public void setColumns (final String columns)
-    {
-        m_reportCfg.setColumns (columns);
-    }
-    
-    public void setSort (final String sort)
-    {
-        m_reportCfg.setSort (sort);
-    }
-    
-    public void setMetrics (final String metrics)
-    {
-        m_reportCfg.setMetrics (metrics);
-    }
-
-    // not supported anymore:
-    
-//    public void setOutdir (final File dir)
-//    {
-//        m_reportCfg.setOutdir (dir);
-//    }
-//    
-//    public void setDestdir (final File dir)
-//    {
-//        m_reportCfg.setDestdir (dir);
-//    }
-    
-    // should not be set at the global level:
-    
-//    public void setOutfile (final String fileName)
-//    {
-//        m_reportCfg.setOutfile (fileName);
-//    }
-    
-    public void setEncoding (final String encoding)
-    {
-        m_reportCfg.setEncoding (encoding);
-    }
-        
-    // protected: .............................................................
-        
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-    
-    private ReportCfg m_reportCfg;   
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant15/com/vladium/emma/ant/IANTVersion.java b/ant/ant15/com/vladium/emma/ant/IANTVersion.java
deleted file mode 100644
index 2a8458d..0000000
--- a/ant/ant15/com/vladium/emma/ant/IANTVersion.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IANTVersion.java,v 1.1.1.1.2.1 2004/07/10 03:34:52 vlad_r Exp $
- */
-package com.vladium.emma.ant;
-
-import java.io.File;
-import java.lang.reflect.Method;
-import java.lang.reflect.Modifier;
-
-import org.apache.tools.ant.types.FileSet;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2004
- */
-public
-interface IANTVersion
-{
-    // public: ................................................................
-    
-    /** 'true' iff the current runtime version is 1.2 or later */
-    boolean ANT_1_5_PLUS = _ANTVersion._ANT_1_5_PLUS; // static final but not inlinable
-    
-    
-    abstract class _ANTVersion
-    {
-        static final boolean _ANT_1_5_PLUS; // set in <clinit>
-        
-        private _ANTVersion () {  /* prevent subclassing */ }
-    
-        static
-        {
-            boolean temp = true;
-            try
-            {
-                final Method m = FileSet.class.getMethod ("setFile", new Class [] { File.class });
-                
-                // [assertion: 'm' is public]
-                
-                final int modifiers = m.getModifiers ();
-                if ((modifiers & Modifier.STATIC) != 0)
-                    temp = false;
-            }
-            catch (NoSuchMethodException nsme)
-            {
-                temp = false;
-            }
-            catch (SecurityException se)
-            {
-                temp = false;
-            }
-            catch (Throwable t)
-            {
-                t.printStackTrace (System.out);
-                temp = false;
-            }
-            
-            _ANT_1_5_PLUS = temp;
-        }
-
-    } // end of nested class
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/ant15/com/vladium/emma/ant/XFileSet.java b/ant/ant15/com/vladium/emma/ant/XFileSet.java
deleted file mode 100644
index 49e0bb2..0000000
--- a/ant/ant15/com/vladium/emma/ant/XFileSet.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: XFileSet.java,v 1.1.1.1 2004/05/09 16:57:28 vlad_r Exp $
- */
-package com.vladium.emma.ant;
-
-import java.io.File;
-
-import org.apache.tools.ant.types.FileSet;
-import org.apache.tools.ant.types.PatternSet;
-
-// ----------------------------------------------------------------------------
-/**
- * An extension of ANT's stock FileSet that adds the convenience of specifying
- * a single 'file' attribute
- * 
- * @author Vlad Roubtsov, (C) 2004
- */
-public
-final class XFileSet extends FileSet
-{
-    // public: ................................................................
-    
-    
-    public XFileSet ()
-    {
-        super ();
-    }
-    
-    public XFileSet (final FileSet fileset)
-    {
-        super (fileset);
-    }
-    
-    
-    // 'file' attribute:
-    public void setFile (final File file)
-    {
-        if (IANTVersion.ANT_1_5_PLUS)
-        {
-            super.setFile (file);
-        }
-        else
-        {
-            if (isReference ()) throw tooManyAttributes ();
-        
-            final File parent = file.getParentFile ();
-            if (parent != null) setDir (parent);
-    
-            final PatternSet.NameEntry include = createInclude ();
-            include.setName (file.getName ());
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-        
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/ant/data/placeholder.exclude b/ant/data/placeholder.exclude
deleted file mode 100644
index e69de29..0000000
--- a/ant/data/placeholder.exclude
+++ /dev/null
diff --git a/ant/res/placeholder.exclude b/ant/res/placeholder.exclude
deleted file mode 100644
index e69de29..0000000
--- a/ant/res/placeholder.exclude
+++ /dev/null
diff --git a/build.xml b/build.xml
deleted file mode 100644
index 0c98e24..0000000
--- a/build.xml
+++ /dev/null
@@ -1,514 +0,0 @@
-<?xml version="1.0"?>
-<!-- ============= [build file for ANT v1.5.x] ====================== -->
-<!DOCTYPE project
-[
-    <!ENTITY dependencies SYSTEM "dependencies.xml" >
-]>
-
-<project name="emma" default="build" basedir="." >
-  <!-- $Id: build.xml,v 1.2.2.3 2005/06/13 00:20:55 vlad_r Exp $ --> 
-  <property name="app.short.name" value="${ant.project.name}" />
-  <property name="app.project.start.date" value="2001/02/01" />
-
-  <!-- TODO: build log --> 
-
-  <!-- ============================================================== -->
-
-  <!-- pull in the OS environment variables; an OS env variable VAR can be used as ${env.VAR}: -->
-  <property environment="env" />
-
-  <!-- ============================================================== -->
-  <!-- build branch properties and local customization overrides: -->
-
-  <!-- first, load the official build settings file: -->
-  <property file="build.properties" />
-  
-  <!-- next, load the CVS-versioned release/branch properties file: -->
-  <property file="release.properties" />
-
-  <!-- next, load an optional global properties file: -->
-  <property file="${env.ANT_BLDENV}/ant.properties" />
-
-  <!-- ============================================================== -->
-  <!-- global compiler settings: -->
-
-  <property name="build.debug" value="on" /> <!-- default for a release build is "on" -->
-  <property name="build.deprecation" value="off" />
-  <property name="build.compiler" value="modern" />
-  <property name="build.sysclasspath" value="ignore" />
-  <property name="build.target" value="1.2" /> <!-- all .class files are stamped as compatible with 1.2 JVMs: -->
-
-  <!-- ============================================================== -->
-  <!-- main/default build target: -->
-
-  <target name="build" depends="dist"
-          description="-> full build [without 'clean']"
-  />
-
-  <!-- helper build subtargets: -->
-
-  <target name="build.core.compile" depends="core.compile"
-          description="-> re-compiles updated core sources [no 'clean']"
-  />
-  <target name="build.core.package" depends="core.package"
-          description="-> re-packages core classes [no 'clean']"
-  />
-
-  <!-- build modifier targets: -->
-
-  <target name="official"
-          description="-> switches 'build' into official, CVS-aware mode" >
-    <property name="build.is.official" value="yes" />
-  </target>
-
-  <target name="release"
-          description="-> [RELEASE]" >
-    <property name="build.is.on.a.branch" value="yes" />
-    <property name="app.build.release.tag" value="" /> <!-- no tag means official release -->
-    <property name="file.release.prefix" value="" />
-    <property name="cvs.ready.label.prefix" value="RELEASE" />
-  </target>
-
-  <target name="stable"
-          description="-> [STABLE]" >
-    <property name="app.build.release.tag" value=" (stable)" />
-    <property name="file.release.prefix" value="-stable" />
-    <property name="cvs.ready.label.prefix" value="STABLE" />
-  </target>
-
-  <!-- ============================================================== -->
-  <!-- init targets: -->
-  <!-- ============================================================== -->
-
-  <!-- static (checked-in) build structure: -->
-  <property file="module.dirs.properties" />
-
-  <!-- work (created by the build) build structure: -->
-  <property file="work.dirs.properties" />
-
-  <target name="init.work.dirs" >
-    <mkdir dir="${out.dir}" />
-    <mkdir dir="${dist.dir}" />
-    <mkdir dir="${release.dir}" />
-    <mkdir dir="${temp.dir}" />
-
-    <mkdir dir="${tools.classes.out.dir}" />
-
-    <mkdir dir="${core.classes.out.dir}" />
-    <mkdir dir="${core.srcgen.out.dir}" />
-    <mkdir dir="${core.res.out.dir}" />
-
-    <mkdir dir="${ant.classes.out.dir}" />
-  </target>
-
-  <target name="init" depends="init.work.dirs">
-    <!-- NOTE: the official build machine sets these explicitly,
-         these unofficial defaults are provided for private builds only: -->
-    <property name="build.target.j2se.14.home" value="${java.home}" />
-    <property name="build.target.j2se.12.home" value="${build.target.j2se.14.home}" />
-    <property name="build.target.j2se.13.home" value="${build.target.j2se.14.home}" />
-
-    <property name="build.target.ant.15.home" value="${env.ANT_HOME}" />
-    <property name="build.target.ant.14.home" value="${build.target.ant.15.home}" />
-
-    
-    <!-- verify that we have J2SE 1.4+: -->
-    <available property="j2se.is.14+" classname="java.lang.CharSequence" />
-    <fail unless="j2se.is.14+">location [${build.target.j2se.14.home}] does not specify J2SE 1.4+</fail>
-
-    <available file="${temp.dir}/.ready.build.stamp" type="file" property="build.is.dirty" value="yes" />
-
-    <!-- include dependencies.xml (a dynamic include by design): -->
-    &dependencies;
-
-    <echo message="ANT version: ${ant.version}" />
-    <echo message="JDK version: ${ant.java.version}" />
-    <echo message="build debug flag: ${build.debug}" />
-  </target>
-
-  <!-- ============================================================== -->
-  <!-- support targets: -->
-  <!-- ============================================================== -->
-
-  <target name="clean" depends="clean.out, clean.dist" description="-> complete clean (output + distribution)" />
-
-  <target name="clean.out" description="-> output clean" >
-    <delete dir="${out.dir}" />
-  </target>
-
-  <target name="clean.dist" description="-> distribution clean" >
-    <delete dir="${dist.dir}"/>
-    <delete dir="${release.dir}"/>
-  </target>
-
-
-  <target name="timestamp" depends="init, -timestamp.1, -timestamp.2, -timestamp.3, -timestamp.4, -timestamp.5">
-  </target>
-
-  <target name="-timestamp.1" depends="init" unless="build.is.dirty" >
-    <java classname="com.vladium.util.version.VersionStampTool"
-          classpathref="lib.internal.classpath"
-          output="${temp.dir}/.ready.build.stamp"
-          append="no"
-    >
-        <arg value="-start" />
-        <arg value="${app.project.start.date}" />
-        <arg value="-format" />
-        <arg value="~F~" />
-    </java>
-    <java classname="com.vladium.util.version.VersionStampTool"
-          classpathref="lib.internal.classpath"
-          output="${temp.dir}/timestamp.properties"
-          append="no"
-    >
-        <arg value="-start" />
-        <arg value="${app.project.start.date}" />
-        <arg value="-fend" />
-        <arg value="${temp.dir}/.ready.build.stamp" />
-        <arg value="-format" />
-        <arg value="app.build.id=${app.build.id.format}\napp.build.date=${app.build.date.format}" />
-    </java>
-    <!-- TODO: this is ugly and breaks private builds (constant appending is bad any way): -->
-    <!-- <echo message="file.release.prefix=${file.release.prefix}" file="${temp.dir}/timestamp.properties" append="yes" /> -->
-  </target>
-
-  <target name="-timestamp.2" depends="init" >
-    <property file="${temp.dir}/timestamp.properties" />
-
-    <!-- private/Eclipse build defaults: -->
-    <property name="app.build.release.tag" value=" (unsupported private build)" />
-    <property name="app.bug.report.link" value="this private build is unsupported" />
-    <property name="file.release.prefix" value="-private" />
-
-    <property name="file.release.label" value="${app.major.version}.${app.minor.version}.${app.build.id}" />
-    <echo message="build id: ${file.release.label}${app.build.release.tag}" />
-  </target>
-
-  <target name="-timestamp.2a" depends="init" if="build.is.on.a.branch" >
-    <property name="cvs.branch.label" value="BRANCH_${app.major.version}_${app.minor.version}" />
-  </target>
-
-  <target name="-timestamp.3" depends="init, -timestamp.2a" if="build.is.official" >
-    <property name="cvs.ready.label" value="${cvs.ready.label.prefix}_${app.major.version}_${app.minor.version}_${app.build.id}" />
-    <property name="cvs.branch.label" value="HEAD" /> <!-- default to a trunk/stable build -->
-    <echo message="CVS branch label: ${cvs.branch.label}" />
-    <echo message="release version (CVS ready label): ${cvs.ready.label}" />
-  </target>
-
-  <target name="-timestamp.4" depends="init, build.cvs.ready" if="build.is.official" >
-  </target>
-
-  <target name="-timestamp.5" depends="init" unless="build.is.dirty" >
-    <copy overwrite="yes" todir="${core.srcgen.out.dir}" >
-      <fileset dir="${core.data.dir}" includes="**/*.java" />
-      <filterset>
-        <filter token="APP_MAJOR_VERSION" value='*/ ${app.major.version}; // ' />
-        <filter token="APP_MINOR_VERSION" value='*/ ${app.minor.version}; // ' />
-        <filter token="APP_BUILD_ID" value='*/ ${app.build.id}; // ' />
-        <filter token="APP_BUILD_RELEASE_TAG" value='*/ "${app.build.release.tag}"; // ' />
-        <filter token="APP_BUILD_DATE" value='*/ "${app.build.date}"; // ' />
-        <filter token="APP_BUG_REPORT_LINK" value='*/ "${app.bug.report.link}"; // ' />
-        <filter token="APP_HOME_SITE_LINK" value='*/ "${app.home.site.link}"; // ' />
-      </filterset>
-    </copy>
-    <copy overwrite="yes" file="${core.data.dir}/MANIFEST.MF" todir="${temp.dir}" >
-      <filterset>
-        <filter token="JDK_ID" value="JDK_${ant.java.version}" />
-        <filter token="BUILD_USER_NAME" value="${user.name} on ${os.name}:${os.version}:${os.arch}" />
-        
-        <filter token="APP_NAME" value="${app.short.name}" />
-        <filter token="APP_MAJOR_VERSION" value="${app.major.version}" />
-        <filter token="APP_MINOR_VERSION" value="${app.minor.version}" />
-        <filter token="APP_BUILD_ID" value="${app.build.id}" />
-        <filter token="APP_BUILD_RELEASE_TAG" value="${app.build.release.tag}" />
-        <filter token="APP_BUILD_DATE" value="${app.build.date}" />
-        <filter token="APP_BUG_REPORT_LINK" value="${app.bug.report.link}" />
-        <filter token="APP_HOME_SITE_LINK" value="${app.home.site.link}" />
-      </filterset>
-    </copy>
-  </target>
-
-  <target name="-pre-compile" depends="init, timestamp" >
-  </target>
-
-  <!-- ============================================================== -->
-  <!-- compilation targets: -->
-  <!-- ============================================================== -->
-
-  <target name="compile" depends="init, core.compile, ant.compile, tools.compile" />
-
-  <!-- ========================== -->
-  <!-- core module: -->
-
-  <target name="core.bootstrap.compile" depends="init, -pre-compile" >
-    <javac destdir="${core.classes.out.dir}"
-           debug="${build.debug}"
-           deprecation="${build.deprecation}"
-           target="${build.target}"
-           bootclasspathref="boot.j2se.12.classpath"
-           extdirs="${ext.j2se.12.classpath}"
-           classpathref="core.classpath"
-    >
-      <!-- include IAppVersion.java: -->
-      <src path="${core.srcgen.out.dir}" />
-
-      <!-- classes used by core.src.java12.dir sources: -->
-      <src path="${core.src.java12.dir}" />
-      <include name="**/util/Property.java" />
-      <include name="**/IAppConstants.java" />
-    </javac>
-  </target>
-
-  <target name="core.java14.compile" depends="init, core.bootstrap.compile" >
-    <javac destdir="${core.classes.out.dir}"
-           debug="${build.debug}"
-           deprecation="${build.deprecation}"
-           target="${build.target}"
-           bootclasspathref="boot.j2se.14.classpath"
-           extdirs="${ext.j2se.14.classpath}"
-           classpathref="core.classpath"
-    >
-      <src path="${core.src.java14.dir}" />
-    </javac>
-  </target>
-
-  <target name="core.java13.compile" depends="init, core.java14.compile" >
-    <javac destdir="${core.classes.out.dir}"
-           debug="${build.debug}"
-           deprecation="${build.deprecation}"
-           target="${build.target}"
-           bootclasspathref="boot.j2se.13.classpath"
-           extdirs="${ext.j2se.13.classpath}"
-           classpathref="core.classpath"
-    >
-      <src path="${core.src.java13.dir}" />
-    </javac>
-  </target>
-
-  <!-- the bulk of core compilation: -->
-  <target name="core.compile" depends="init, core.java13.compile" >
-    <javac destdir="${core.classes.out.dir}"
-           debug="${build.debug}"
-           deprecation="${build.deprecation}"
-           target="${build.target}"
-           bootclasspathref="boot.j2se.12.classpath"
-           extdirs="${ext.j2se.12.classpath}"
-           classpathref="core.classpath"
-    >
-      <src path="${core.src.java12.dir}" />
-      <exclude name="**/util/Property.java" />
-      <exclude name="**/IAppConstants.java" />
-    </javac>
-  </target>
-
-  <!-- ========================== -->
-  <!-- tools module: -->
-
-  <target name="tools.compile" depends="init, core.compile" >
-    <javac destdir="${tools.classes.out.dir}"
-           debug="${build.debug}"	
-           deprecation="${build.deprecation}"
-           target="${build.target}"
-           bootclasspathref="boot.j2se.14.classpath"
-           extdirs="${ext.j2se.14.classpath}"
-           classpathref="tools.classpath"
-    >
-      <src path="${tools.src.dir}" />
-    </javac>
-  </target>
-
-  <!-- ========================== -->
-  <!-- ant module: -->
-
-  <target name="ant.15.compile" depends="init, core.compile" >
-    <javac destdir="${ant.classes.out.dir}"
-           debug="${build.debug}"
-           deprecation="${build.deprecation}"
-           target="${build.target}"
-           bootclasspathref="boot.j2se.12.classpath"
-           extdirs="${ext.j2se.12.classpath}"
-           classpathref="ant.15.classpath"
-    >
-      <src path="${ant.src.ant15.dir}" />
-    </javac>
-  </target>
-
-  <!-- the bulk of ant compilation: -->
-  <target name="ant.compile" depends="init, core.compile, ant.15.compile" >
-    <javac destdir="${ant.classes.out.dir}"
-           debug="${build.debug}"
-           deprecation="${build.deprecation}"
-           target="${build.target}"
-           bootclasspathref="boot.j2se.12.classpath"
-           extdirs="${ext.j2se.12.classpath}"
-           classpathref="ant.14.classpath"
-    >
-      <src path="${ant.src.ant14.dir}" />
-    </javac>
-  </target>
-
-
-  <!-- ============================================================== -->
-  <!-- packaging targets: -->
-  <!-- ============================================================== -->
-
-  <target name="package" depends="init, core.package, ant.package" />
-
-  <!-- ========================== -->
-  <!-- run tools: -->
-  
-  <target name="rtclosure.gen" depends="init, compile" >
-    <property name="rtclosure.resource" value="com/vladium/emma/rt/RTExitHook.closure" />
-    <property name="rtclosure.classpath" refid="core.classpath" />
-
-    <java classname="com.vladium.tools.ClassDep"
-          classpathref="tools.classpath"
-    >
-      <arg value="${rtclosure.classpath}" />
-      <arg value="${core.res.out.dir}/${rtclosure.resource}" />
-      <arg value="com.vladium.emma.rt.RTExitHook" />
-      <arg value="com.vladium.emma.data.CoverageData" />
-    </java>
-  </target>
-
-  <!-- ========================== -->
-  <!-- core module: -->
-
-  <target name="core.package"  depends="init, core.compile, rtclosure.gen" >
-    <jar jarfile="${out.dir}/${app.short.name}.jar"
-         manifest="${temp.dir}/MANIFEST.MF"
-         compress="true"
-         index="false"
-     >
-      <!-- classes: -->
-      <fileset dir="${core.classes.out.dir}" includes="**/*.class" />
-      <!-- classloader resources: -->
-      <fileset dir="${core.res.dir}" excludes="**/*.exclude" />
-      <fileset dir="${core.res.out.dir}" excludes="**/*.exclude" />
-      <manifest>
-        <attribute name="Main-Class" value="${app.short.name}run" />
-      </manifest>
-    </jar>
-  </target>
-
-  <!-- ========================== -->
-  <!-- ant module: -->
-
-  <target name="ant.package"  depends="init, ant.compile" >
-    <jar jarfile="${out.dir}/${app.short.name}_ant.jar"
-         manifest="${temp.dir}/MANIFEST.MF"
-         compress="true"
-         index="false"
-     >
-      <!-- classes: -->
-      <fileset dir="${ant.classes.out.dir}" includes="**/*.class" />
-      <!-- classloader resources: -->
-      <fileset dir="${ant.res.dir}" excludes="**/*.exclude" />
-      <manifest>
-        <attribute name="Main-Class" value="com.vladium.${app.short.name}.ANTMain" />
-      </manifest>
-    </jar>
-  </target>
-
-  <!-- ============================================================== -->
-  <!-- distribution targets: -->
-  <!-- ============================================================== -->
-
-  <target name="dist" depends="init, core.dist, ant.dist" />
-
-  <!-- ========================== -->
-  <!-- core module: -->
-  <target name="core.dist" depends="init, core.package" >
-    <copy file="${out.dir}/${app.short.name}.jar" todir="${dist.dir}" />
-  </target>
-
-  <!-- ========================== -->
-  <!-- ant module: -->
-  <target name="ant.dist" depends="init, ant.package" >
-    <copy file="${out.dir}/${app.short.name}_ant.jar" todir="${dist.dir}" />
-  </target>
-
-  <!-- ============================================================== -->
-  <!-- file release targets: -->
-  <!-- ============================================================== -->
-
-  <target name="publish.release" depends="init, release, publish.property.check, release.lib, release.full, release.src" >
-  </target>
-
-  <target name="publish.stable" depends="init, stable, publish.property.check, release.lib" >
-    <fail unless="file.release.label">need ${file.release.label}</fail>
-  </target>
-	
-  <target name="publish.property.check" depends="init" >
-    <fail unless="file.release.label">property ${file.release.label} must be set</fail>
-    <fail unless="docs.dist.dir">property ${docs.dist.dir} must be set</fail>
-    <property name="publish.ok" value="true" />
-  </target> 
-
-
-  <target name="release.lib" depends="init" if="publish.ok" >
-    <!-- lib distribution: -->
-    <zip destfile="${release.dir}/${app.short.name}${file.release.prefix}-${file.release.label}-lib.zip"
-         basedir="${dist.dir}"
-         includes="*.jar"
-    />
-  </target>
-
-  <target name="release.src" depends="init" if="publish.ok" >
-    <!-- source files: --> 
-    <zip destfile="${release.dir}/${app.short.name}-${file.release.label}-src.zip" >
-      <zipfileset prefix="${app.short.name}-${file.release.label}"
-                  dir="${basedir}"
-                  includes="${tools}/**, ${core}/**, ${ant}/**, ${lib}/**"
-                  excludes="*/CVS/*"
-      />
-      <!-- license, build script and instructions, etc: --> 
-      <zipfileset prefix="${app.short.name}-${file.release.label}"
-                  dir="${basedir}"
-                  includes="*.txt, *.xml, *.html, *.properties"
-                  excludes="build.properties"
-      />
-    </zip>
-  </target>
-
-  <target name="release.full" depends="init" if="publish.ok" >
-    <zip destfile="${release.dir}/${app.short.name}-${file.release.label}.zip" >
-      <!-- license: -->
-      <zipfileset prefix="${app.short.name}-${file.release.label}"
-                  dir="${basedir}/"
-                  includes="cpl*.html"
-      />
-      <!-- examples and related instructions: -->
-      <zipfileset prefix="${app.short.name}-${file.release.label}"
-                  dir="${basedir}/install/data"
-      />
-      <!-- lib distribution: -->
-      <zipfileset prefix="${app.short.name}-${file.release.label}/lib"
-                  dir="${dist.dir}"
-                  includes="*.jar"
-      />
-      <!-- doc distribution: -->
-      <zipfileset prefix="${app.short.name}-${file.release.label}/docs"
-                  dir="${docs.dist.dir}/docs"
-      />
-    </zip>
-  </target>
-
-
-  <!-- ============================================================== -->
-  <!-- CVS targets: -->
-  <!-- ============================================================== -->
-
-  <target name="build.cvs.ready" if="cvs.ready.label">
-    <cvs failonerror="yes" output="${out.dir}/cvs.txt" error="${out.dir}/cvs.error.txt"
-         command="-t rtag -r ${cvs.branch.label} -F -a ${cvs.ready.label} ${app.short.name}" />
-  </target>
-
-  <target name="build.cvs.unready" if="cvs.ready.label">
-    <cvs failonerror="yes" output="${out.dir}/cvs.txt" error="${out.dir}/cvs.error.txt"
-         command="-t rtag -r ${cvs.branch.label} -d -a ${cvs.ready.label} ${app.short.name}" />
-  </target>
-
-</project>
-<!-- ========= END OF FILE ========================================== -->
-
diff --git a/core/data/MANIFEST.MF b/core/data/MANIFEST.MF
deleted file mode 100644
index 72deeac..0000000
--- a/core/data/MANIFEST.MF
+++ /dev/null
@@ -1,7 +0,0 @@
-Manifest-Version: 1.0
-Created-By: @JDK_ID@
-Specification-Title: @APP_NAME@
-Specification-Vendor: (C) Vladimir Roubtsov
-Implementation-Vendor: @BUILD_USER_NAME@
-Specification-Version: @APP_MAJOR_VERSION@.@APP_MINOR_VERSION@
-Implementation-Version: @APP_MAJOR_VERSION@.@APP_MINOR_VERSION@.@APP_BUILD_ID@@APP_BUILD_RELEASE_TAG@ (@APP_BUILD_DATE@)
diff --git a/core/data/com/vladium/app/IAppVersion.java b/core/data/com/vladium/app/IAppVersion.java
deleted file mode 100644
index 07966f3..0000000
--- a/core/data/com/vladium/app/IAppVersion.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IAppVersion.java,v 1.1.1.1 2004/05/09 16:57:28 vlad_r Exp $
- */
-package com.vladium.app;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IAppVersion
-{
-    // public: ................................................................
-
-
-    // filled in by the build:
-    
-    int APP_MAJOR_VERSION = /* @APP_MAJOR_VERSION@ */ 0;
-    int APP_MINOR_VERSION = /* @APP_MINOR_VERSION@ */ 0;
-
-    int APP_BUILD_ID = /* @APP_BUILD_ID@ */ 0;
-    String APP_BUILD_RELEASE_TAG = /* @APP_BUILD_RELEASE_TAG@ */ " (unsupported private build)";
-    String APP_BUILD_DATE = /* @APP_BUILD_DATE@ */ "unknown";
-
-    String APP_BUG_REPORT_LINK = /* @APP_BUG_REPORT_LINK@ */ "this private build is unsupported";
-    String APP_HOME_SITE_LINK = /* @APP_HOME_SITE_LINK@ */ "this private build is unsupported";
-
-    // derived properties [must be compile-time consts]:
-
-    String APP_BUILD_ID_AND_TAG = "" + APP_BUILD_ID + APP_BUILD_RELEASE_TAG;
-    
-    String APP_VERSION = "" + APP_MAJOR_VERSION + "." + APP_MINOR_VERSION;
-    String APP_VERSION_WITH_BUILD_ID_AND_TAG = APP_VERSION + "." + APP_BUILD_ID_AND_TAG;
-
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/emma/AppLoggers.java b/core/java12/com/vladium/emma/AppLoggers.java
deleted file mode 100644
index 21437ed..0000000
--- a/core/java12/com/vladium/emma/AppLoggers.java
+++ /dev/null
@@ -1,90 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AppLoggers.java,v 1.1.2.1 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import java.util.HashSet;
-import java.util.Set;
-import java.util.StringTokenizer;
-
-import com.vladium.logging.ILogLevels;
-import com.vladium.logging.Logger;
-import com.vladium.util.IProperties;
-import com.vladium.util.Strings;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2004
- */
-public
-abstract class AppLoggers
-{
-    // public: ................................................................
-    
-    public static final String PREFIX_VERBOSITY                 = "verbosity.";
-
-    public static final String PROPERTY_VERBOSITY_LEVEL         = PREFIX_VERBOSITY + "level";
-    public static final String DEFAULT_VERBOSITY_LEVEL          = ILogLevels.INFO_STRING;
-    
-    public static final String PROPERTY_VERBOSITY_FILTER        = PREFIX_VERBOSITY + "filter";
-    
-    public static Logger create (final String appName, final IProperties properties, final Logger base)
-    {
-        if (properties == null)
-            throw new IllegalArgumentException ("null input: properties");
-        
-        // verbosity level:
-        
-        final int level;
-        {
-            final String _level = properties.getProperty (PROPERTY_VERBOSITY_LEVEL,
-                                                          DEFAULT_VERBOSITY_LEVEL);
-            level = Logger.stringToLevel (_level);
-        }
-        
-        // verbosity filter:
-        
-        final Set filter;
-        {
-            final String _filter = properties.getProperty (PROPERTY_VERBOSITY_FILTER);
-            Set temp = null;
-            
-            if (_filter != null)
-            {
-                final StringTokenizer tokenizer = new StringTokenizer (_filter, COMMA_DELIMITERS);
-                if (tokenizer.countTokens () > 0)
-                {
-                    temp = new HashSet (tokenizer.countTokens ());
-                    while (tokenizer.hasMoreTokens ())
-                    {
-                        temp.add (tokenizer.nextToken ());
-                    }
-                }
-            }
-            
-            filter = temp;
-        }
-        
-        return Logger.create (level, null, appName, filter, base);
-    }
-    
-    
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-
-    private AppLoggers () {} // this class is not extendible
-    
-    private static final String COMMA_DELIMITERS    = "," + Strings.WHITE_SPACE;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/Command.java b/core/java12/com/vladium/emma/Command.java
deleted file mode 100644
index c453605..0000000
--- a/core/java12/com/vladium/emma/Command.java
+++ /dev/null
@@ -1,326 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Command.java,v 1.1.1.1.2.1 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import java.io.File;
-import java.io.IOException;
-import java.io.PrintWriter;
-import java.util.Properties;
-
-import com.vladium.logging.ILogLevels;
-import com.vladium.util.IConstants;
-import com.vladium.util.Property;
-import com.vladium.util.Strings;
-import com.vladium.util.XProperties;
-import com.vladium.util.args.IOptsParser;
-import com.vladium.emma.data.mergeCommand;
-import com.vladium.emma.instr.instrCommand;
-import com.vladium.emma.report.reportCommand;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class Command
-{
-    // public: ................................................................
-    
-    
-    public static Command create (final String name, final String usageName, final String [] args)
-    {
-        final Command tool;
-        
-        // TODO: dynamic load here?
-        
-        if ("run".equals (name))
-            tool = new runCommand (usageName, args);
-        else if ("instr".equals (name))
-            tool = new instrCommand (usageName, args);
-        else if ("report".equals (name))
-            tool = new reportCommand (usageName, args);
-        else if ("merge".equals (name))
-            tool = new mergeCommand (usageName, args);
-        else
-            throw new IllegalArgumentException ("unknown command: [" + name + "]");    
-            
-        tool.initialize ();
-        
-        return tool;
-    }
-    
-    public abstract void run ();
-    
-    // protected: .............................................................
-
-    
-    protected Command (final String usageToolName, final String [] args)
-    {
-        m_usageToolName = usageToolName;
-        m_args = args != null ? (String []) args.clone () : IConstants.EMPTY_STRING_ARRAY;  
-    }
-    
-    protected abstract String usageArgsMsg ();
-
-    // TODO: is this useful (separate from <init>)?
-    protected void initialize ()
-    {
-        m_exit = false;
-        
-        if (m_out != null) try { m_out.flush (); } catch (Throwable ignore) {}
-        m_out = new PrintWriter (System.out, true);
-    }   
-    
-    protected final String getToolName ()
-    {
-        // TODO: embed build number etc
-        final String clsName = getClass ().getName ();
-        
-        return clsName.substring (0, clsName.length () - 7);
-    }
-    
-    protected final IOptsParser getOptParser (final ClassLoader loader)
-    {
-        return IOptsParser.Factory.create (usageResName (getToolName ()), loader,
-            usageMsgPrefix (m_usageToolName), USAGE_OPT_NAMES);
-    } 
-    
-    protected final boolean processOpt (final IOptsParser.IOpt opt)
-    {
-        final String on = opt.getCanonicalName ();
-        
-        if ("exit".equals (on)) // 'exit' should always be first in this else-if chain
-        {
-            m_exit = getOptionalBooleanOptValue (opt);
-            return true;
-        }
-        else if ("p".equals (on))
-        {
-            m_propertyFile = new File (opt.getFirstValue ());
-            return true;
-        }
-        else if ("verbose".equals (on))
-        {
-            setPropertyOverride (AppLoggers.PROPERTY_VERBOSITY_LEVEL, ILogLevels.VERBOSE_STRING);
-            return true;
-        }
-        else if ("quiet".equals (on))
-        {
-            setPropertyOverride (AppLoggers.PROPERTY_VERBOSITY_LEVEL, ILogLevels.WARNING_STRING);
-            return true;
-        }
-        else if ("silent".equals (on))
-        {
-            setPropertyOverride (AppLoggers.PROPERTY_VERBOSITY_LEVEL, ILogLevels.SEVERE_STRING);
-            return true;
-        }
-        else if ("debug".equals (on))
-        {
-            if (opt.getValueCount () == 0)
-                setPropertyOverride (AppLoggers.PROPERTY_VERBOSITY_LEVEL, ILogLevels.TRACE1_STRING);
-            else
-                setPropertyOverride (AppLoggers.PROPERTY_VERBOSITY_LEVEL, opt.getFirstValue ());
-            
-            return true;
-        }
-        else if ("debugcls".equals (on))
-        {
-            setPropertyOverride (AppLoggers.PROPERTY_VERBOSITY_FILTER, Strings.toListForm (Strings.merge (opt.getValues (), COMMA_DELIMITERS, true), ',')); 
-            return true;
-        }
-        
-        return false;
-    }
-    
-    protected final void processCmdPropertyOverrides (final IOptsParser.IOpts parsedopts)
-    {
-        final IOptsParser.IOpt [] popts = parsedopts.getOpts (EMMAProperties.GENERIC_PROPERTY_OVERRIDE_PREFIX);
-        if ((popts != null) && (popts.length != 0))
-        {
-            final Properties cmdOverrides = new XProperties ();
-            
-            for (int o = 0; o < popts.length; ++ o)
-            {
-                final IOptsParser.IOpt opt = popts [o];
-                final String on = opt.getName ().substring (opt.getPatternPrefix ().length ());
-                
-                // TODO: support mergeable prefixed opts?
-                
-                cmdOverrides.setProperty (on, opt.getFirstValue ());
-            }
-            
-            // command line user overrides are have highest precedence:
-            m_propertyOverrides = Property.combine (cmdOverrides, m_propertyOverrides);
-        }
-    }
-    
-    protected final boolean processFilePropertyOverrides ()
-    {
-        if (m_propertyFile != null)
-        {
-            final Properties fileOverrides;
-            
-            try
-            {
-                fileOverrides = Property.getPropertiesFromFile (m_propertyFile);
-            }
-            catch (IOException ioe)
-            {
-                exit (true, "property override file [" + m_propertyFile.getAbsolutePath () + "] could not be read", ioe, RC_USAGE);
-                return false;
-            }
-            
-            // props file overrides have second highest precendence:
-            m_propertyOverrides = Property.combine (m_propertyOverrides, fileOverrides); 
-        }
-        
-        return true;
-    }
-    
-    protected final void usageexit (final IOptsParser parser, final int level, final String msg)
-    {
-        if (msg != null)
-        {
-            m_out.print (usageMsgPrefix (m_usageToolName));
-            m_out.println (msg);
-        }
-        
-        if (parser != null)
-        {
-            m_out.println ();
-            m_out.print (usageMsgPrefix (m_usageToolName));
-            m_out.println (toolNameToCommandName (m_usageToolName) + " " + usageArgsMsg () + ",");
-            m_out.println ("  where options include:");
-            m_out.println ();
-            parser.usage (m_out, level, STDOUT_WIDTH);            
-        }
-        
-        m_out.println ();
-        exit (true, null, null, RC_USAGE);
-    }
-    
-    protected final void exit (final boolean showBuildID, final String msg, final Throwable t, final int rc)
-        throws EMMARuntimeException
-    {
-        if (showBuildID)
-        {
-            m_out.println (IAppConstants.APP_USAGE_BUILD_ID);
-        }
-        
-        if (msg != null)
-        {
-            m_out.print (toolNameToCommandName (m_usageToolName) + ": "); m_out.println (msg);
-        }
-
-        if (rc != RC_OK)
-        {
-            // error exit:
-            
-            //if ((showBuildID) || (msg != null)) m_out.println ();
-            
-            if (m_exit)
-            {
-                if (t != null) t.printStackTrace (m_out);
-                System.exit (rc);
-            }
-            else
-            {
-                if (t instanceof EMMARuntimeException)
-                    throw (EMMARuntimeException) t;
-                else if (t != null)
-                    throw msg != null ? new EMMARuntimeException (msg, t) : new EMMARuntimeException ("unexpected failure: ", t);
-            }
-        }
-        else
-        {
-            // normal exit: 't' is ignored
-            
-            if (m_exit)
-            {
-                System.exit (0);
-            }
-        }
-    }
-
-    protected static boolean getOptionalBooleanOptValue (final IOptsParser.IOpt opt)
-    {
-        if (opt.getValueCount () == 0)
-            return true;
-        else
-        {
-            final String v = opt.getFirstValue ().toLowerCase ();
-         
-            return Property.toBoolean (v);
-        }
-    }
-    
-    protected static String [] getListOptValue (final IOptsParser.IOpt opt, final String delimiters, final boolean processAtFiles)
-        throws IOException
-    {
-        return Strings.mergeAT (opt.getValues (), delimiters, processAtFiles);
-    }
-    
-    protected static String usageMsgPrefix (final String toolName)
-    {
-        return toolNameToCommandName (toolName).concat (" usage: ");
-    }
-    
-    protected static String usageResName (final String toolName)
-    {
-        return toolName.replace ('.', '/').concat ("_usage.res");
-    }
-    
-    protected static String toolNameToCommandName (final String toolName)
-    {
-        final int lastDot = toolName.lastIndexOf ('.');
-        
-        return lastDot > 0 ? toolName.substring (lastDot + 1) : toolName;
-    }
-    
-
-    protected final String m_usageToolName;
-    protected final String [] m_args;
-    
-    protected File m_propertyFile;
-    protected Properties m_propertyOverrides;
-    protected boolean m_exit;
-    protected PrintWriter m_out; // this is set independently from Logger by design
-    
-    protected static final String COMMA_DELIMITERS    = "," + Strings.WHITE_SPACE;
-    protected static final String PATH_DELIMITERS     = ",".concat (File.pathSeparator);
-
-    protected static final String [] USAGE_OPT_NAMES = new String [] {"h", "help"};
-    protected static final int STDOUT_WIDTH = 80;    
-    
-    // return codes used with System.exit():
-    protected static final int RC_OK          = 0;
-    protected static final int RC_USAGE       = 1;
-    protected static final int RC_UNEXPECTED  = 2;
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-
-    /*
-     * Lazily instantiates m_propertyOverrides if necessary.
-     */
-    private void setPropertyOverride (final String key, final String value)
-    {
-        Properties propertyOverrides = m_propertyOverrides;
-        if (propertyOverrides == null)
-        {
-            m_propertyOverrides = propertyOverrides = new XProperties ();
-        }
-        
-        propertyOverrides.setProperty (key, value);
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/EMMAException.java b/core/java12/com/vladium/emma/EMMAException.java
deleted file mode 100644
index 9a42f9e..0000000
--- a/core/java12/com/vladium/emma/EMMAException.java
+++ /dev/null
@@ -1,94 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: EMMAException.java,v 1.1.1.1 2004/05/09 16:57:29 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import com.vladium.util.exception.AbstractException;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-class EMMAException extends AbstractException
-{
-    // public: ................................................................
-
-    /**
-     * Constructs an exception with null message and null cause.
-     */    
-    public EMMAException ()
-    {
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and null cause.
-     *
-     * @param message the detail message [can be null]
-     */
-    public EMMAException (final String message)
-    {
-        super (message);
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and null cause.
-     *   
-     * @param message the detail message [can be null]
-     * @param arguments message format parameters [can be null or empty]
-     *
-     * @see java.text.MessageFormat
-     */
-    public EMMAException (final String message, final Object [] arguments)
-    {
-        super (message, arguments);
-    }
-    
-    /**
-     * Constructs an exception with null error message/code and given cause.
-     *
-     * @param cause the cause [nested exception] [can be null]
-     */
-    public EMMAException (final Throwable cause)
-    {
-        super (cause);
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and given cause.
-     *
-     * @param message the detail message [can be null]
-     * @param cause the cause [nested exception] [can be null]
-     */
-    public EMMAException (final String message, final Throwable cause)
-    {
-        super (message, cause);
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and given cause.
-     *
-     * @param message the detail message [can be null]
-     * @param arguments message format parameters [can be null or empty]
-     * @param cause the cause [nested exception] [can be null]
-     *
-     * @see java.text.MessageFormat
-     */
-    public EMMAException (final String message, final Object [] arguments, final Throwable cause)
-    {
-        super (message, arguments, cause);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/emma/EMMAProperties.java b/core/java12/com/vladium/emma/EMMAProperties.java
deleted file mode 100644
index 14bfba4..0000000
--- a/core/java12/com/vladium/emma/EMMAProperties.java
+++ /dev/null
@@ -1,202 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: EMMAProperties.java,v 1.1.1.1.2.3 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import java.io.File;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.Map;
-import java.util.Properties;
-import java.util.WeakHashMap;
-
-import com.vladium.util.ClassLoaderResolver;
-import com.vladium.util.IProperties;
-import com.vladium.util.Property;
-import com.vladium.emma.report.IReportProperties;
-import com.vladium.emma.report.ReportProperties;
-
-// ----------------------------------------------------------------------------
-/**
- * A reflection of "${IAppConstants.APP_PROPERTY_RES_NAME}.properties" resource
- * as viewed by a given classloader.
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class EMMAProperties
-{
-    // public: ................................................................
-    
-    public static final String GENERIC_PROPERTY_OVERRIDE_PREFIX = "D";
-
-    // [the DEFAULT_xxx settings duplicate the defaults in APP_DEFAULT_PROPERTIES_RES_NAME
-    // resource to provide a safe fallback option if that resource cannot be loaded]
-    
-    public static final String DEFAULT_META_DATA_OUT_FILE       = "coverage.em";
-    public static final Boolean DEFAULT_META_DATA_OUT_MERGE     = Boolean.TRUE;
-    public static final String PREFIX_META_DATA                 = "metadata.";
-    public static final String PROPERTY_META_DATA_OUT_FILE      = PREFIX_META_DATA + "out.file";
-    public static final String PROPERTY_META_DATA_OUT_MERGE     = PREFIX_META_DATA + "out.merge";
-    
-    public static final String DEFAULT_COVERAGE_DATA_OUT_FILE   = "coverage.ec";
-    public static final Boolean DEFAULT_COVERAGE_DATA_OUT_MERGE = Boolean.TRUE;
-    public static final String PREFIX_COVERAGE_DATA             = "coverage.";
-    public static final String PROPERTY_COVERAGE_DATA_OUT_FILE  = PREFIX_COVERAGE_DATA + "out.file";
-    public static final String PROPERTY_COVERAGE_DATA_OUT_MERGE = PREFIX_COVERAGE_DATA + "out.merge";
-
-    public static final String DEFAULT_SESSION_DATA_OUT_FILE    = "coverage.es";
-    public static final Boolean DEFAULT_SESSION_DATA_OUT_MERGE  = Boolean.TRUE;
-    public static final String PREFIX_SESSION_DATA              = "session.";
-    public static final String PROPERTY_SESSION_DATA_OUT_FILE   = PREFIX_SESSION_DATA + "out.file";
-    public static final String PROPERTY_SESSION_DATA_OUT_MERGE  = PREFIX_SESSION_DATA + "out.merge";
-    
-    public static final String PROPERTY_TEMP_FILE_EXT           = ".et";
-    
-    public static final Map SYSTEM_PROPERTY_REDIRECTS; // set in <clinit>
-    
-    
-    /**
-     * Global method used to create an appearance that all app work has been
-     * done at the same point in time (useful for setting archive and report
-     * timestamps etc).
-     * 
-     * @return the result of System.currentTimeMillis (), evaluated on the
-     * first call only
-     */
-    public static synchronized long getTimeStamp ()
-    {
-        long result = s_timestamp;
-        if (result == 0)
-        {
-            s_timestamp = result = System.currentTimeMillis ();
-        }
-
-        return result; 
-    }
-    
-    
-    public static String makeAppVersion (final int major, final int minor, final int build)
-    {
-        final StringBuffer buf = new StringBuffer ();
-        
-        buf.append (major);
-        buf.append ('.');
-        buf.append (minor);
-        buf.append ('.');
-        buf.append (build);
-        
-        return buf.toString ();
-    }
-    
-    
-    /**
-     * Wraps a Properties into a IProperties with the app's standard property
-     * mapping in place.
-     * 
-     * @param properties [null results in null result]
-     */
-    public static IProperties wrap (final Properties properties)
-    {
-        if (properties == null) return null;
-        
-        return IProperties.Factory.wrap (properties, ReportProperties.REPORT_PROPERTY_MAPPER);
-    }
-   
-    /**
-     * Retrieves application properties as classloader resource with a given name.
-     * [as seen from ClassLoaderResolver.getClassLoader ()]. The result is cached
-     * using this loader as a weak key.
-     * 
-     * @return properties [can be null]
-     */
-    public static synchronized IProperties getAppProperties ()
-    {
-        final ClassLoader loader = ClassLoaderResolver.getClassLoader ();
-        
-        return getAppProperties (loader);
-    }
-
-    public static synchronized IProperties getAppProperties (final ClassLoader loader)
-    {
-        IProperties properties = (IProperties) s_properties.get (loader);
-
-        if (properties != null)
-            return properties;
-        else
-        {
-            final String appName = IAppConstants.APP_NAME_LC;
-            
-            // note: this does not use Property.getAppProperties() by design,
-            // because that mechanism is not property alias-capable
-            
-            final IProperties systemRedirects = wrap (Property.getSystemPropertyRedirects (EMMAProperties.SYSTEM_PROPERTY_REDIRECTS));
-            final IProperties appDefaults = wrap (Property.getProperties (appName + "_default.properties", loader));
-            final IProperties systemFile;
-            {
-                final String fileName = Property.getSystemProperty (appName + ".properties");
-                final File file = fileName != null
-                    ? new File (fileName)
-                    : null;
-
-                systemFile = wrap (Property.getLazyPropertiesFromFile (file));
-            }
-            final IProperties system = wrap (Property.getSystemProperties (appName));
-            final IProperties userOverrides = wrap (Property.getProperties (appName + ".properties", loader));
-            
-            // "vertical" inheritance order:
-            //      (1) user overrides ("emma.properties" classloader resource)
-            //      (2) system properties (java.lang.System.getProperties(),
-            //                             filtered by the app prefix)
-            //      (3) system file properties ("emma.properties" system property,
-            //                                  interpreted as a property file)
-            //      (4) app defaults ("emma_default.properties" classloader resource)
-            //      (5) system property redirects (report.out.encoding->file.encoding,
-            //                                     report.out.dir->user.dir, etc)
-        
-            properties = IProperties.Factory.combine (userOverrides,
-                         IProperties.Factory.combine (system,
-                         IProperties.Factory.combine (systemFile,
-                         IProperties.Factory.combine (appDefaults,
-                                                      systemRedirects))));
-
-            s_properties.put (loader, properties);
-            
-            return properties;
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private EMMAProperties () {} // prevent subclassing
-        
-    
-    private static long s_timestamp;
-    
-    private static final Map /* ClassLoader->Properties */ s_properties; // set in <clinit>
-    
-    static
-    {
-        s_properties = new WeakHashMap ();
-        
-        final Map redirects = new HashMap ();
-        redirects.put (IReportProperties.PREFIX.concat (IReportProperties.OUT_ENCODING),
-                       "file.encoding");
-        redirects.put (IReportProperties.PREFIX.concat (IReportProperties.OUT_DIR),
-                       "user.dir");
-                       
-        SYSTEM_PROPERTY_REDIRECTS = Collections.unmodifiableMap (redirects);
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/emma/EMMARuntimeException.java b/core/java12/com/vladium/emma/EMMARuntimeException.java
deleted file mode 100644
index 2f7883d..0000000
--- a/core/java12/com/vladium/emma/EMMARuntimeException.java
+++ /dev/null
@@ -1,94 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: EMMARuntimeException.java,v 1.1.1.1 2004/05/09 16:57:29 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import com.vladium.util.exception.AbstractRuntimeException;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-class EMMARuntimeException extends AbstractRuntimeException
-{
-    // public: ................................................................
-
-    /**
-     * Constructs an exception with null message and null cause.
-     */    
-    public EMMARuntimeException ()
-    {
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and null cause.
-     *
-     * @param message the detail message [can be null]
-     */
-    public EMMARuntimeException (final String message)
-    {
-        super (message);
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and null cause.
-     *   
-     * @param message the detail message [can be null]
-     * @param arguments message format parameters [can be null or empty]
-     *
-     * @see java.text.MessageFormat
-     */
-    public EMMARuntimeException (final String message, final Object [] arguments)
-    {
-        super (message, arguments);
-    }
-    
-    /**
-     * Constructs an exception with null error message/code and given cause.
-     *
-     * @param cause the cause [nested exception] [can be null]
-     */
-    public EMMARuntimeException (final Throwable cause)
-    {
-        super (cause);
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and given cause.
-     *
-     * @param message the detail message [can be null]
-     * @param cause the cause [nested exception] [can be null]
-     */
-    public EMMARuntimeException (final String message, final Throwable cause)
-    {
-        super (message, cause);
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and given cause.
-     *
-     * @param message the detail message [can be null]
-     * @param arguments message format parameters [can be null or empty]
-     * @param cause the cause [nested exception] [can be null]
-     *
-     * @see java.text.MessageFormat
-     */
-    public EMMARuntimeException (final String message, final Object [] arguments, final Throwable cause)
-    {
-        super (message, arguments, cause);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/emma/IAppConstants.java b/core/java12/com/vladium/emma/IAppConstants.java
deleted file mode 100644
index d5feb6b..0000000
--- a/core/java12/com/vladium/emma/IAppConstants.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IAppConstants.java,v 1.1.1.1.2.2 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import com.vladium.app.IAppVersion;
-import com.vladium.jcd.lib.Types;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IAppConstants extends IAppVersion
-{
-    // public: ................................................................
-    
-    String APP_NAME         = "EMMA";
-    String APP_NAME_LC      = "emma";
-    String APP_COPYRIGHT    = "(C) Vladimir Roubtsov";
-    String APP_THROWABLE_BUILD_ID   = "[" + APP_NAME + " v" + APP_VERSION_WITH_BUILD_ID_AND_TAG + "]";
-    String APP_USAGE_BUILD_ID   = "[" + APP_NAME + " v" + APP_VERSION + ", build " + APP_BUILD_ID_AND_TAG + "]";
-    String APP_VERBOSE_BUILD_ID = "[" + APP_NAME + " v" + APP_VERSION + ", build " + APP_BUILD_ID_AND_TAG + " (" + APP_BUILD_DATE + ")]";
-    
-    String APP_USAGE_PREFIX = APP_NAME + " usage: ";
-    
-    String APP_PACKAGE = Types.getClassPackageName (IAppConstants.class);
-    
-    long DATA_FORMAT_VERSION    = 0x20L;
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/IAppErrorCodes.java b/core/java12/com/vladium/emma/IAppErrorCodes.java
deleted file mode 100644
index d07c9b8..0000000
--- a/core/java12/com/vladium/emma/IAppErrorCodes.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IAppErrorCodes.java,v 1.1.1.1 2004/05/09 16:57:29 vlad_r Exp $
- */
-package com.vladium.emma;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IAppErrorCodes
-{
-    // public: ................................................................
-    
-    /** {throwable.toString(), bug report link} */
-    String UNEXPECTED_FAILURE       = "UNEXPECTED_FAILURE";
-    
-    /** {parameter name, value} */
-    String INVALID_PARAMETER_VALUE  = "INVALID_PARAMETER_VALUE";
-    
-    /** {value} */
-    String INVALID_COLUMN_NAME      = "INVALID_COLUMN_NAME";
-    
-    /** {parameter name} */
-    String REQUIRED_PARAMETER_MISSING = "REQUIRED_PARAMETER_MISSING"; 
-    
-    /** {app name} */
-    String SECURITY_RESTRICTION                 = "SECURITY_RESTRICTION:";
-    
-    /** {app name, appclassname, app classloader name} */
-    String MAIN_CLASS_BAD_DELEGATION            = "MAIN_CLASS_BAD_DELEGATION";
-    
-    /** {classname} */
-    String MAIN_CLASS_NOT_FOUND                 = "MAIN_CLASS_NOT_FOUND";
-    
-    /** {classname, throwable.toString()} */
-    String MAIN_CLASS_LOAD_FAILURE              = "MAIN_CLASS_LOAD_FAILURE";
-    
-    /** {classname} */
-    String MAIN_METHOD_NOT_FOUND                = "MAIN_METHOD_NOT_FOUND";
-    
-    /** {classname, throwable.toString()} */
-    String MAIN_METHOD_FAILURE                  = "MAIN_METHOD_FAILURE";
-    
-    //TODO: /** ?? */
-    String REPORT_GEN_FAILURE                   = "REPORT_GEN_FAILURE";    
-    
-    /** [none] */
-    String REPORT_IO_FAILURE                    = "REPORT_IO_FAILURE";
-    
-    /** {classname} */
-    String CLASS_STAMP_MISMATCH                 = "CLASS_STAMP_MISMATCH";
-    
-    /** {dir} */
-    String OUT_MKDIR_FAILURE                    = "OUT_MKDIR_FAILURE";
-    
-    /** [none] */
-    String INSTR_IO_FAILURE                     = "INSTR_IO_FAILURE";
-    
-    /** {filename} */
-    String OUT_IO_FAILURE                       = "OUT_IO_FAILURE";
-    
-    /** [none] */
-    String ARGS_IO_FAILURE                      = "ARGS_IO_FAILURE";
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/Processor.java b/core/java12/com/vladium/emma/Processor.java
deleted file mode 100644
index 0701030..0000000
--- a/core/java12/com/vladium/emma/Processor.java
+++ /dev/null
@@ -1,119 +0,0 @@
-/* Copyright (C) 2004 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Processor.java,v 1.1.2.1 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import java.util.Properties;
-
-import com.vladium.logging.Logger;
-import com.vladium.util.IProperties;
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2004
- */
-public
-abstract class Processor
-{
-    // public: ................................................................
-
-
-    public synchronized void run ()
-    {
-        validateState ();
-        
-        // load tool properties:
-        final IProperties toolProperties;
-        {
-            final IProperties appProperties = EMMAProperties.getAppProperties ();
-            
-            toolProperties = IProperties.Factory.combine (m_propertyOverrides, appProperties);
-        }
-        if ($assert.ENABLED) $assert.ASSERT (toolProperties != null, "toolProperties is null"); // can be empty, though
-
-        final Logger current = Logger.getLogger ();
-        final Logger log = AppLoggers.create (m_appName, toolProperties, current);
-        
-        if (log.atTRACE1 ())
-        {
-            log.trace1 ("run", "complete tool properties:");
-            toolProperties.list (log.getWriter ());
-        }
-        
-        try
-        {
-            Logger.push (log);
-            m_log = log;
-        
-            _run (toolProperties);
-        }
-        finally
-        {
-            if (m_log != null)
-            {
-                Logger.pop (m_log);
-                m_log = null;
-            }
-        }
-    }
-
-    
-    public synchronized final void setAppName (final String appName)
-    {
-        m_appName = appName;
-    }
-    
-    /**
-     * 
-     * @param overrides [may be null (unsets the previous overrides)]
-     */
-    public synchronized final void setPropertyOverrides (final Properties overrides)
-    {
-        m_propertyOverrides = EMMAProperties.wrap (overrides);
-    }
-    
-    /**
-     * 
-     * @param overrides [may be null (unsets the previous overrides)]
-     */
-    public synchronized final void setPropertyOverrides (final IProperties overrides)
-    {
-        m_propertyOverrides = overrides;
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected Processor ()
-    {
-        // not publicly instantiable
-    }
-
-    protected abstract void _run (IProperties toolProperties);
-
-    
-    protected void validateState ()
-    {
-        // no Processor state needs validation
-        
-        // [m_appName allowed to be null]
-        // [m_propertyOverrides allowed to be null]
-    }
-    
-    
-    protected String m_appName; // used as logging prefix, can be null
-    protected IProperties m_propertyOverrides; // user override; can be null/empty for run()
-    protected Logger m_log; // not null only within run()
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/ClassDescriptor.java b/core/java12/com/vladium/emma/data/ClassDescriptor.java
deleted file mode 100644
index d2595b6..0000000
--- a/core/java12/com/vladium/emma/data/ClassDescriptor.java
+++ /dev/null
@@ -1,231 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ClassDescriptor.java,v 1.1.1.1 2004/05/09 16:57:30 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.DataInput;
-import java.io.DataOutput;
-import java.io.IOException;
-import java.io.Serializable;
-
-import com.vladium.util.IConstants;
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class ClassDescriptor implements IConstants, Serializable
-{
-    // public: ................................................................
-    
-    
-    public ClassDescriptor (final String packageVMName, final String name, final long stamp,
-                            final String srcFileName,
-                            final MethodDescriptor [] methods)
-    {
-        if (packageVMName == null)
-            throw new IllegalArgumentException ("null input: packageVMName");
-        if (name == null)
-            throw new IllegalArgumentException ("null input: name");
-        if (methods == null)
-            throw new IllegalArgumentException ("null input: methods");
-        
-        if ($assert.ENABLED)
-        {
-            for (int m = 0; m < methods.length; ++ m)
-            {
-                $assert.ASSERT (methods [m] != null, "methods [" + m + "] = null (length = " + methods.length + ")");
-            }
-        }
-        
-        m_packageVMName = packageVMName;
-        m_name = name;
-        m_stamp = stamp;
-        m_srcFileName = srcFileName;
-        m_methods = methods; // TODO: defensive copy?
-        
-        boolean completeLineNumberInfo = true;
-        for (int m = 0; m < m_methods.length; ++ m)
-        {
-            final MethodDescriptor method = methods [m];
-            
-            if (((method.getStatus () & IMetadataConstants.METHOD_NO_BLOCK_DATA) == 0) && ! m_methods [m].hasLineNumberInfo ())
-            {
-                completeLineNumberInfo = false;
-                break;
-            }
-        }
-        
-        m_hasCompleteLineNumberInfo = completeLineNumberInfo;
-    }
-    
-    
-    // equality is defined based on <m_packageVMName, m_name> only (m_stamp not mixed in by design):
-    
-    public final boolean equals (final Object rhs)
-    {
-        if (! (rhs instanceof ClassDescriptor)) return false;
-        
-        final ClassDescriptor _rhs = (ClassDescriptor) rhs;
-        
-        if (hashCode () != _rhs.hashCode ()) return false;
-        
-        if (! m_name.equals (_rhs.m_name)) return false;
-        if (! m_packageVMName.equals (_rhs.m_packageVMName)) return false;
-        
-        return true;
-    }
-    
-    public final int hashCode ()
-    {
-        if (m_hash == 0)
-        {
-            final int hash = m_name.hashCode () + 16661 * m_packageVMName.hashCode ();
-            m_hash = hash;
-            
-            return hash;
-        }
-        
-        return m_hash;
-    }
-    
-    
-    public final String getPackageVMName ()
-    {
-        return m_packageVMName;
-    }
-    
-    public final String getName ()
-    {
-        return m_name;
-    }
-    
-    public final long getStamp ()
-    {
-        return m_stamp;
-    }
-    
-    public final String getClassVMName ()
-    {
-        // TODO: use Descriptors API?
-        if (m_packageVMName.length () == 0)
-            return m_name;
-        else
-            return new StringBuffer (m_packageVMName).append ("/").append (m_name).toString ();
-    }
-    
-    public final String getSrcFileName ()
-    {
-        return m_srcFileName;
-    }
-    
-    public final MethodDescriptor [] getMethods ()
-    {
-        return m_methods; // no defensive copy
-    }
-    
-    public final boolean hasSrcFileInfo ()
-    {
-        return m_srcFileName != null;
-    }
-    
-    public final boolean hasCompleteLineNumberInfo ()
-    {
-        return m_hasCompleteLineNumberInfo;
-    }
-    
-    
-    public String toString ()
-    {
-        return toString ("");
-    }
-    
-    public String toString (final String indent)
-    {
-        StringBuffer s = new StringBuffer (indent + "class [" + (m_packageVMName.length () > 0 ? m_packageVMName + "/" : "") + m_name + "] descriptor:");
-        
-        for (int m = 0; m < m_methods.length; ++ m)
-        {
-            s.append (EOL);
-            s.append (m_methods [m].toString (indent + INDENT_INCREMENT));
-        }
-        
-        return s.toString ();
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    static ClassDescriptor readExternal (final DataInput in)
-        throws IOException
-    {
-        final String packageVMName = in.readUTF ();
-        final String name = in.readUTF ();
-        
-        final long stamp = in.readLong ();
-        
-        final byte srcFileNameFlag = in.readByte ();
-        final String srcFileName = srcFileNameFlag != 0 ? in.readUTF () : null;
-        
-        final int length = in.readInt ();
-        final MethodDescriptor [] methods = new MethodDescriptor [length];
-        for (int i = 0; i < length; ++ i)
-        {
-            methods [i] = MethodDescriptor.readExternal (in);
-        }
-        
-        return new ClassDescriptor (packageVMName, name, stamp, srcFileName, methods);
-    }
-    
-    static void writeExternal (final ClassDescriptor cls, final DataOutput out)
-        throws IOException
-    {
-        out.writeUTF (cls.m_packageVMName);
-        out.writeUTF (cls.m_name);
-        
-        out.writeLong (cls.m_stamp);
-        
-        if (cls.m_srcFileName != null)
-        {
-            out.writeByte (1);
-            out.writeUTF (cls.m_srcFileName);
-        }
-        else
-        {
-            out.writeByte (0);
-        }
-        
-        final MethodDescriptor [] methods = cls.m_methods;
-        final int length = methods.length;
-        out.writeInt (length);
-        for (int i = 0; i < length; ++ i)
-        {
-            MethodDescriptor.writeExternal (methods [i], out);
-        }
-        
-        // [m_hash and m_hasCompleteLineNumberInfo are transient data]
-    }
-    
-    // private: ...............................................................
-    
-    
-    private final String m_packageVMName; // in JVM format, no trailing '/' [never null]
-    private final String m_name; // relative to (m_packageName + '/') [never null]
-    private final long m_stamp;
-    private final String m_srcFileName; // relative to (m_packageName + '/') [can be null]
-    private final MethodDescriptor [] m_methods; // [never null, could be empty]
-    
-    private final boolean m_hasCompleteLineNumberInfo;
-    private transient int m_hash;
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/emma/data/CoverageData.java b/core/java12/com/vladium/emma/data/CoverageData.java
deleted file mode 100644
index 540756c..0000000
--- a/core/java12/com/vladium/emma/data/CoverageData.java
+++ /dev/null
@@ -1,230 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CoverageData.java,v 1.1.1.1 2004/05/09 16:57:31 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.DataInput;
-import java.io.DataOutput;
-import java.io.IOException;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Map;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-final class CoverageData implements ICoverageData, Cloneable
-{
-    // public: ................................................................
-    
-    // TODO: duplicate issue
-       
-    public Object lock ()
-    {
-        return m_coverageMap;
-    }
-    
-    public ICoverageData shallowCopy ()
-    {
-        final CoverageData _clone;
-        try
-        {
-            _clone = (CoverageData) super.clone ();
-        }
-        catch (CloneNotSupportedException cnse)
-        {
-            throw new Error (cnse.toString ());
-        }
-        
-        final HashMap _coverageMap;
-        
-        synchronized (lock ())
-        {
-            _coverageMap = (HashMap) m_coverageMap.clone ();
-        }
-        
-        _clone.m_coverageMap = _coverageMap;
-        
-        return _clone;
-    }
-    
-    public int size ()
-    {
-        return m_coverageMap.size (); 
-    }
-
-    public DataHolder getCoverage (final ClassDescriptor cls)
-    {
-        if (cls == null) throw new IllegalArgumentException ("null input: cls");
-        
-        return (DataHolder) m_coverageMap.get (cls.getClassVMName ());
-    }
-    
-    public void addClass (final boolean [][] coverage, final String classVMName, final long stamp)
-    {
-        m_coverageMap.put (classVMName, new DataHolder (coverage, stamp));
-    }
-    
-    // IMergeable:
-    
-    public boolean isEmpty ()
-    {
-        return m_coverageMap.isEmpty ();
-    }
-
-    /*
-     * This method is not MT-safe wrt addClass() etc.
-     * 
-     * note: rhs entries override current entries if they have different stamps;
-     * otherwise, the data is merged 
-     */    
-    public IMergeable merge (final IMergeable rhs)
-    {
-        if ((rhs == null) || rhs.isEmpty () || (rhs == this))
-            return this;
-        else
-        {
-            final CoverageData rhscdata = (CoverageData) rhs; // TODO: redesign so that the cast is not necessary
-            final Map rhscoverageData = rhscdata.m_coverageMap;
-            
-            for (Iterator entries = rhscoverageData.entrySet ().iterator (); entries.hasNext (); )
-            {
-                final Map.Entry entry = (Map.Entry) entries.next ();
-                final String classVMName = (String) entry.getKey ();
-                
-                final DataHolder rhsdata = (DataHolder) entry.getValue ();
-                // [assertion: rhsdata != null]
-                
-                final DataHolder data = (DataHolder) m_coverageMap.get (classVMName);
-                
-                if (data == null)
-                    m_coverageMap.put (classVMName, rhsdata);
-                else
-                {
-                    if (rhsdata.m_stamp != data.m_stamp)
-                        m_coverageMap.put (classVMName, rhsdata);
-                    else // merge two runtime profiles
-                    {
-                        final boolean [][] rhscoverage = rhsdata.m_coverage;
-                        final boolean [][] coverage = data.m_coverage;
-                        
-                        // [assertion: both coverage and rhscoverage aren't null]
-                    
-                        if ($assert.ENABLED) $assert.ASSERT (coverage.length == rhscoverage.length, "coverage.length [" + coverage.length + "] != rhscoverage.length [" + rhscoverage.length + "]");
-                        for (int m = 0, mLimit = coverage.length; m < mLimit; ++ m)
-                        {
-                            final boolean [] rhsmcoverage = rhscoverage [m];
-                            final boolean [] mcoverage = coverage [m];
-                            
-                            if (mcoverage == null)
-                            {
-                                if ($assert.ENABLED) $assert.ASSERT (rhsmcoverage == null, "mcoverage == null but rhsmcoverage != null");
-                                
-                                // [nothing to merge]
-                            }
-                            else
-                            {
-                                if ($assert.ENABLED) $assert.ASSERT (rhsmcoverage != null, "mcoverage != null but rhsmcoverage == null");
-                                if ($assert.ENABLED) $assert.ASSERT (mcoverage.length == rhsmcoverage.length, "mcoverage.length [" + mcoverage.length + "] != rhsmcoverage.length [" + rhsmcoverage.length + "]");
-                                
-                                for (int b = 0, bLimit = mcoverage.length; b < bLimit; ++ b)
-                                {
-                                    if (rhsmcoverage [b]) mcoverage [b] = true;
-                                }
-                            }
-                        }
-                    }
-                }
-            }
-                
-            return this;
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    CoverageData ()
-    {
-        m_coverageMap = new HashMap ();
-    }
-    
-    
-    static CoverageData readExternal (final DataInput in)
-        throws IOException
-    {
-        final int size = in.readInt ();
-        final HashMap coverageMap = new HashMap (size);
-        
-        for (int i = 0; i < size; ++ i)
-        {
-            final String classVMName = in.readUTF ();
-            final long stamp = in.readLong ();
-            
-            final int length = in.readInt ();
-            final boolean [][] coverage = new boolean [length][];
-            for (int c = 0; c < length; ++ c) 
-            {
-                coverage [c] = DataFactory.readBooleanArray (in);
-            }
-            
-            coverageMap.put (classVMName, new DataHolder (coverage, stamp));
-        }
-        
-        return new CoverageData (coverageMap);
-    }
-    
-    static void writeExternal (final CoverageData cdata, final DataOutput out)
-        throws IOException
-    {
-        final Map coverageMap = cdata.m_coverageMap;
-        
-        final int size = coverageMap.size ();
-        out.writeInt (size);
-        
-        final Iterator entries = coverageMap.entrySet ().iterator ();
-        for (int i = 0; i < size; ++ i)
-        {
-            final Map.Entry entry = (Map.Entry) entries.next ();
-            
-            final String classVMName = (String) entry.getKey ();
-            final DataHolder data = (DataHolder) entry.getValue ();
-            
-            final boolean [][] coverage = data.m_coverage;
-            
-            out.writeUTF (classVMName);
-            out.writeLong (data.m_stamp);
-            
-            final int length = coverage.length;
-            out.writeInt (length);
-            for (int c = 0; c < length; ++ c)
-            {
-                DataFactory.writeBooleanArray (coverage [c], out);
-            }
-        }
-    }
-
-    // private: ...............................................................
-    
-    
-    private CoverageData (final HashMap coverageMap)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (coverageMap != null, "coverageMap is null");
-        m_coverageMap = coverageMap;
-    }
-    
-    
-    private /*final*/ HashMap /* String(classVMName) -> DataHolder */ m_coverageMap; // never null
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/CoverageOptions.java b/core/java12/com/vladium/emma/data/CoverageOptions.java
deleted file mode 100644
index 5a688c7..0000000
--- a/core/java12/com/vladium/emma/data/CoverageOptions.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CoverageOptions.java,v 1.1.1.1.2.1 2004/06/27 22:58:26 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.DataInput;
-import java.io.DataOutput;
-import java.io.IOException;
-import java.io.Serializable;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class CoverageOptions implements Serializable
-{
-    // public: ................................................................
-    
-    public boolean excludeSyntheticMethods ()
-    {
-        return m_excludeSyntheticMethods;
-    }
-    
-    public boolean excludeBridgeMethods ()
-    {
-        return m_excludeBridgeMethods;
-    }
-    
-    public boolean doSUIDCompensation ()
-    {
-        return m_doSUIDCompensation;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    /*
-     * Package-private to be accessble by CoverageOptionsFactory
-     * (the factory is in a separate source file to avoid spurious
-     * classloading dependency via InnerClasses attr)
-     */
-    CoverageOptions (final boolean excludeSyntheticMethods,
-                     final boolean excludeBridgeMethods,
-                     final boolean doSUIDCompensation)
-    {
-        m_excludeSyntheticMethods = excludeSyntheticMethods;
-        m_excludeBridgeMethods = excludeBridgeMethods;
-        m_doSUIDCompensation = doSUIDCompensation;
-    }
-    
-    
-    static CoverageOptions readExternal (final DataInput in)
-        throws IOException
-    {
-        return new CoverageOptions (in.readBoolean (),
-                                    in.readBoolean (),
-                                    in.readBoolean ());
-    }
-    
-    static void writeExternal (final CoverageOptions options, final DataOutput out)
-        throws IOException
-    {
-        out.writeBoolean (options.m_excludeSyntheticMethods);
-        out.writeBoolean (options.m_excludeBridgeMethods);
-        out.writeBoolean (options.m_doSUIDCompensation);
-    }
-    
-    // private: ...............................................................
-
-    
-    private final boolean m_excludeSyntheticMethods;
-    private final boolean m_excludeBridgeMethods;
-    private final boolean m_doSUIDCompensation;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/CoverageOptionsFactory.java b/core/java12/com/vladium/emma/data/CoverageOptionsFactory.java
deleted file mode 100644
index af548c3..0000000
--- a/core/java12/com/vladium/emma/data/CoverageOptionsFactory.java
+++ /dev/null
@@ -1,70 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CoverageOptionsFactory.java,v 1.1.2.1 2004/06/27 22:58:26 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.util.Properties;
-
-import com.vladium.emma.instr.InstrProcessor;
-import com.vladium.util.IProperties;
-import com.vladium.util.Property;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2004
- */
-public
-abstract class CoverageOptionsFactory
-{
-    // public: ................................................................
-
-    public static CoverageOptions create (final Properties properties)
-    {
-        final boolean excludeSyntheticMethods =
-            Property.toBoolean (properties.getProperty (InstrProcessor.PROPERTY_EXCLUDE_SYNTHETIC_METHODS,
-                                                        InstrProcessor.DEFAULT_EXCLUDE_SYNTHETIC_METHODS));
-                                                                        
-        final boolean excludeBridgeMethods =
-            Property.toBoolean (properties.getProperty (InstrProcessor.PROPERTY_EXCLUDE_BRIDGE_METHODS,
-                                                        InstrProcessor.DEFAULT_EXCLUDE_BRIDGE_METHODS));
-                                                                                            
-        final boolean doSUIDCompensaton =
-            Property.toBoolean (properties.getProperty (InstrProcessor.PROPERTY_DO_SUID_COMPENSATION,
-                                                        InstrProcessor.DEFAULT_DO_SUID_COMPENSATION));
-        
-        return new CoverageOptions (excludeSyntheticMethods, excludeBridgeMethods, doSUIDCompensaton);
-    }
-    
-    public static CoverageOptions create (final IProperties properties)
-    {
-        final boolean excludeSyntheticMethods =
-            Property.toBoolean (properties.getProperty (InstrProcessor.PROPERTY_EXCLUDE_SYNTHETIC_METHODS,
-                                                        InstrProcessor.DEFAULT_EXCLUDE_SYNTHETIC_METHODS));
-        
-        final boolean excludeBridgeMethods =
-            Property.toBoolean (properties.getProperty (InstrProcessor.PROPERTY_EXCLUDE_BRIDGE_METHODS,
-                                                        InstrProcessor.DEFAULT_EXCLUDE_BRIDGE_METHODS));
-                                                                                         
-        final boolean doSUIDCompensaton =
-            Property.toBoolean (properties.getProperty (InstrProcessor.PROPERTY_DO_SUID_COMPENSATION,
-                                                        InstrProcessor.DEFAULT_DO_SUID_COMPENSATION));
-        
-        return new CoverageOptions (excludeSyntheticMethods, excludeBridgeMethods, doSUIDCompensaton);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-
-    private CoverageOptionsFactory () {} // this class is not extendible
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/DataFactory.java b/core/java12/com/vladium/emma/data/DataFactory.java
deleted file mode 100644
index e4d493e..0000000
--- a/core/java12/com/vladium/emma/data/DataFactory.java
+++ /dev/null
@@ -1,813 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: DataFactory.java,v 1.1.1.1.2.3 2004/07/16 23:32:29 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.BufferedInputStream;
-import java.io.BufferedOutputStream;
-import java.io.DataInput;
-import java.io.DataInputStream;
-import java.io.DataOutput;
-import java.io.DataOutputStream;
-import java.io.File;
-import java.io.FileDescriptor;
-import java.io.FileInputStream;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.ObjectInputStream;
-import java.io.ObjectOutputStream;
-import java.io.OutputStream;
-import java.io.RandomAccessFile;
-import java.net.URL;
-import java.net.URLConnection;
-
-import com.vladium.logging.Logger;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.IAppConstants;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class DataFactory
-{
-    // public: ................................................................
-    
-    // TODO: file compaction
-    // TODO: file locking
-    
-    // TODO: what's the best place for these?
-    
-    public static final byte TYPE_METADATA          = 0x0; // must start with 0
-    public static final byte TYPE_COVERAGEDATA      = 0x1; // must be consistent with mergeload()
-    
-    
-    public static IMergeable [] load (final File file)
-        throws IOException
-    {
-        if (file == null) throw new IllegalArgumentException ("null input: file");
-        
-        return mergeload (file);
-    }
-    
-    public static void persist (final IMetaData data, final File file, final boolean merge)
-        throws IOException
-    {
-        if (data == null) throw new IllegalArgumentException ("null input: data");
-        if (file == null) throw new IllegalArgumentException ("null input: file");
-        
-        if (! merge && file.exists ())
-        {
-            if (! file.delete ())
-                throw new IOException ("could not delete file [" + file.getAbsolutePath () + "]");
-        }
-        
-        persist (data, TYPE_METADATA, file);
-    }
-    
-    public static void persist (final ICoverageData data, final File file, final boolean merge)
-        throws IOException
-    {
-        if (data == null) throw new IllegalArgumentException ("null input: data");
-        if (file == null) throw new IllegalArgumentException ("null input: file");
-        
-        if (! merge && file.exists ())
-        {
-            if (! file.delete ())
-                throw new IOException ("could not delete file [" + file.getAbsolutePath () + "]");
-        }
-        
-        persist (data, TYPE_COVERAGEDATA, file);
-    } 
-    
-    public static void persist (final ISessionData data, final File file, final boolean merge)
-        throws IOException
-    {
-        if (data == null) throw new IllegalArgumentException ("null input: data");
-        if (file == null) throw new IllegalArgumentException ("null input: file");
-        
-        if (! merge && file.exists ())
-        {
-            if (! file.delete ())
-                throw new IOException ("could not delete file [" + file.getAbsolutePath () + "]");
-        }
-        
-        persist (data.getMetaData (), TYPE_METADATA, file); 
-        persist (data.getCoverageData (), TYPE_COVERAGEDATA, file);
-    }
-
-    
-    public static IMetaData newMetaData (final CoverageOptions options)
-    {
-        return new MetaData (options);
-    }
-    
-    public static ICoverageData newCoverageData ()
-    {
-        return new CoverageData (); 
-    }
-
-    public static IMetaData readMetaData (final URL url)
-        throws IOException, ClassNotFoundException
-    {
-        ObjectInputStream oin = null;
-        
-        try
-        {
-            oin = new ObjectInputStream (new BufferedInputStream (url.openStream (), 32 * 1024));
-            
-            return (IMetaData) oin.readObject ();
-        }
-        finally
-        {
-            if (oin != null) try { oin.close (); } catch (Exception ignore) {} 
-        }
-    }
-    
-    public static void writeMetaData (final IMetaData data, final OutputStream out)
-        throws IOException
-    {
-        ObjectOutputStream oout = new ObjectOutputStream (out);
-        oout.writeObject (data);
-    }
-    
-    public static void writeMetaData (final IMetaData data, final URL url)
-        throws IOException
-    {
-        final URLConnection connection = url.openConnection ();
-        connection.setDoOutput (true);
-        
-        OutputStream out = null;
-        try
-        {
-            out = connection.getOutputStream ();
-            
-            writeMetaData (data, out);
-            out.flush ();
-        }
-        finally
-        {
-            if (out != null) try { out.close (); } catch (Exception ignore) {} 
-        }
-    }
-    
-    public static ICoverageData readCoverageData (final URL url)
-        throws IOException, ClassNotFoundException
-    {
-        ObjectInputStream oin = null;
-        
-        try
-        {
-            oin = new ObjectInputStream (new BufferedInputStream (url.openStream (), 32 * 1024));
-            
-            return (ICoverageData) oin.readObject ();
-        }
-        finally
-        {
-            if (oin != null) try { oin.close (); } catch (Exception ignore) {} 
-        }
-    }
-    
-    public static void writeCoverageData (final ICoverageData data, final OutputStream out)
-        throws IOException
-    {
-        // TODO: prevent concurrent modification problems here
-        
-        ObjectOutputStream oout = new ObjectOutputStream (out);
-        oout.writeObject (data);
-    }
-    
-    public static int [] readIntArray (final DataInput in)
-        throws IOException
-    {
-        final int length = in.readInt ();
-        if (length == NULL_ARRAY_LENGTH)
-            return null;
-        else
-        {
-            final int [] result = new int [length];
-            
-            // read array in reverse order:
-            for (int i = length; -- i >= 0; )
-            {
-                result [i] = in.readInt ();
-            }
-            
-            return result;
-        }
-    }
-    
-    public static boolean [] readBooleanArray (final DataInput in)
-        throws IOException
-    {
-        final int length = in.readInt ();
-        if (length == NULL_ARRAY_LENGTH)
-            return null;
-        else
-        {
-            final boolean [] result = new boolean [length];
-            
-            // read array in reverse order:
-            for (int i = length; -- i >= 0; )
-            {
-                result [i] = in.readBoolean ();
-            }
-            
-            return result;
-        }
-    }
-    
-    public static void writeIntArray (final int [] array, final DataOutput out)
-        throws IOException
-    {
-        if (array == null)
-            out.writeInt (NULL_ARRAY_LENGTH);
-        else
-        {
-            final int length = array.length;
-            out.writeInt (length);
-            
-            // write array in reverse order:
-            for (int i = length; -- i >= 0; )
-            {
-                out.writeInt (array [i]);
-            }
-        }
-    }
-    
-    public static void writeBooleanArray (final boolean [] array, final DataOutput out)
-        throws IOException
-    {
-        if (array == null)
-            out.writeInt (NULL_ARRAY_LENGTH);
-        else
-        {
-            final int length = array.length;
-            out.writeInt (length);
-            
-            // write array in reverse order:
-            for (int i = length; -- i >= 0; )
-            {
-                out.writeBoolean (array [i]);
-            }
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-
-    private static final class UCFileInputStream extends FileInputStream
-    {
-        public void close ()
-        {
-        }
-        
-        UCFileInputStream (final FileDescriptor fd)
-        {
-            super (fd);
-            
-            if ($assert.ENABLED) $assert.ASSERT (fd.valid (), "UCFileInputStream.<init>: FD invalid");
-        }
-        
-    } // end of nested class
-
-    private static final class UCFileOutputStream extends FileOutputStream
-    {
-        public void close ()
-        {
-        }
-        
-        UCFileOutputStream (final FileDescriptor fd)
-        {
-            super (fd);
-            
-            if ($assert.ENABLED) $assert.ASSERT (fd.valid (), "UCFileOutputStream.<init>: FD invalid");
-        }
-        
-    } // end of nested class
-
-    
-    private static final class RandomAccessFileInputStream extends BufferedInputStream
-    {
-        public final int read () throws IOException
-        {
-            final int rc = super.read ();
-            if (rc >= 0) ++ m_count;
-            
-            return rc;
-        }
-
-        public final int read (final byte [] b, final int off, final int len)
-            throws IOException
-        {
-            final int rc = super.read (b, off, len);
-            if (rc >= 0) m_count += rc;
-            
-            return rc;
-        }
-
-        public final int read (final byte [] b) throws IOException
-        {
-            final int rc = super.read (b);
-            if (rc >= 0) m_count += rc;
-            
-            return rc;
-        }
-        
-        public void close ()
-        {
-        }        
-
-
-        RandomAccessFileInputStream (final RandomAccessFile raf, final int bufSize)
-            throws IOException
-        {
-            super (new UCFileInputStream (raf.getFD ()), bufSize);
-        }
-        
-        final long getCount ()
-        {
-            return m_count;
-        }
-        
-        private long m_count;
-
-    } // end of nested class
-    
-    private static final class RandomAccessFileOutputStream extends BufferedOutputStream
-    {
-        public final void write (final byte [] b, final int off, final int len) throws IOException
-        {
-            super.write (b, off, len);
-            m_count += len;
-        }
-
-        public final void write (final byte [] b) throws IOException
-        {
-            super.write (b);
-            m_count += b.length;
-        }
-
-        public final void write (final int b) throws IOException
-        {
-            super.write (b);
-            ++ m_count;
-        }
-        
-        public void close ()
-        {
-        }
-        
-        
-        RandomAccessFileOutputStream (final RandomAccessFile raf, final int bufSize)
-            throws IOException
-        {
-            super (new UCFileOutputStream (raf.getFD ()), bufSize);
-        }
-        
-        final long getCount ()
-        {
-            return m_count;
-        }
-        
-        private long m_count;
-
-    } // end of nested class
-    
-    
-    private DataFactory () {} // prevent subclassing   
-
-    /*
-     * input checked by the caller
-     */
-    private static IMergeable [] mergeload (final File file)
-        throws IOException
-    {
-        final Logger log = Logger.getLogger ();
-        final boolean trace1 = log.atTRACE1 ();
-        final boolean trace2 = log.atTRACE2 ();
-        final String method = "mergeload";
-        
-        long start = 0, end;
-        
-        if (trace1) start = System.currentTimeMillis ();
-        
-        final IMergeable [] result = new IMergeable [2];
-        
-        if (! file.exists ())
-        {
-            throw new IOException ("input file does not exist: [" + file.getAbsolutePath () +  "]");
-        }
-        else
-        {
-            RandomAccessFile raf = null;
-            try
-            {
-                raf = new RandomAccessFile (file, "r");
-                
-                // 'file' is a valid existing file, but it could still be of 0 length or otherwise corrupt:
-                final long length = raf.length ();
-                if (trace1) log.trace1 (method, "[" + file + "]: file length = " + length);
-                
-                if (length < FILE_HEADER_LENGTH)
-                {
-                    throw new IOException ("file [" + file.getAbsolutePath () + "] is corrupt or was not created by " + IAppConstants.APP_NAME);
-                }
-                else
-                {
-                    // TODO: data version checks parallel to persist()
-                    
-                    if (length > FILE_HEADER_LENGTH) // return {null, null} in case of equality
-                    {
-                        raf.seek (FILE_HEADER_LENGTH);
-                                
-                        // [assertion: file length > FILE_HEADER_LENGTH]
-                        
-                        // read entries until the first corrupt entry or the end of the file:
-                        
-                        long position = FILE_HEADER_LENGTH;
-                        long entryLength;
-                        
-                        long entrystart = 0;
-                        
-                        while (true)
-                        {
-                            if (trace2) log.trace2 (method, "[" + file + "]: position " + raf.getFilePointer ());
-                            if (position >= length) break;
-                            
-                            entryLength = raf.readLong ();
-                            
-                            if ((entryLength <= 0) || (position + entryLength + ENTRY_HEADER_LENGTH > length))
-                                break;
-                            else
-                            {
-                                final byte type = raf.readByte ();
-                                if ((type < 0) || (type >= result.length))
-                                    break;
-                                    
-                                if (trace2) log.trace2 (method, "[" + file + "]: found valid entry of size " + entryLength + " and type " + type);
-                                {
-                                    if (trace2) entrystart = System.currentTimeMillis ();
-                                    final IMergeable data = readEntry (raf, type, entryLength);
-                                    if (trace2) log.trace2 (method, "entry read in " + (System.currentTimeMillis () - entrystart) + " ms");                                    
-                                    
-                                    final IMergeable current = result [type];
-                                    
-                                    if (current == null)
-                                        result [type] = data;
-                                    else
-                                        result [type] = current.merge (data); // note: later entries overrides earlier entries
-                                }
-                                
-                                position += entryLength + ENTRY_HEADER_LENGTH;
-                                
-                                if ($assert.ENABLED) $assert.ASSERT (raf.getFD ().valid (), "FD invalid"); 
-                                raf.seek (position);
-                            }
-                        }                        
-                    }
-                }
-            }
-            finally
-            {
-                if (raf != null) try { raf.close (); } catch (Throwable ignore) {}
-                raf = null;
-            }
-        }
-        
-        if (trace1)
-        {
-            end = System.currentTimeMillis ();
-            
-            log.trace1 (method, "[" + file + "]: file processed in " + (end - start) + " ms"); 
-        }
-        
-        return result;
-    }
-
-
-    /*
-     * input checked by the caller
-     */
-    private static void persist (final IMergeable data, final byte type, final File file)
-        throws IOException
-    {
-        final Logger log = Logger.getLogger ();
-        final boolean trace1 = log.atTRACE1 ();
-        final boolean trace2 = log.atTRACE2 ();
-        final String method = "persist";
-        
-        long start = 0, end;
-        
-        if (trace1) start = System.currentTimeMillis ();
-        
-        // TODO: 1.4 adds some interesting RAF open mode options as well
-        // TODO: will this benefit from extra buffering?
-        
-        // TODO: data version checks
-
-        RandomAccessFile raf = null;
-        try
-        {
-            boolean overwrite = false;
-            boolean truncate = false;
-                        
-            if (file.exists ())
-            {
-                // 'file' exists:
-                
-                if (! file.isFile ()) throw new IOException ("can persist in normal files only: " + file.getAbsolutePath ());
-                
-                raf = new RandomAccessFile (file, "rw");
-                
-                // 'file' is a valid existing file, but it could still be of 0 length or otherwise corrupt:
-                final long length = raf.length ();
-                if (trace1) log.trace1 (method, "[" + file + "]: existing file length = " + length);
-                
-                
-                if (length < 4)
-                {
-                    overwrite = true;
-                    truncate = (length > 0);
-                }
-                else
-                {
-                    // [assertion: file length >= 4]
-                    
-                    // check header info before reading further:
-                    final int magic = raf.readInt ();
-                    if (magic != MAGIC)
-                        throw new IOException ("cannot overwrite [" + file.getAbsolutePath () + "]: not created by " + IAppConstants.APP_NAME);
-                    
-                    if (length < FILE_HEADER_LENGTH)
-                    {
-                        // it's our file, but the header is corrupt: overwrite
-                        overwrite = true;
-                        truncate = true;
-                    }  
-                    else
-                    {
-                        // [assertion: file length >= FILE_HEADER_LENGTH]
-                        
-//                        if (! append)
-//                        {
-//                            // overwrite any existing data:
-//                            
-//                            raf.seek (FILE_HEADER_LENGTH);
-//                            writeEntry (raf, FILE_HEADER_LENGTH, data, type);
-//                        }
-//                        else
-                        {
-                            // check data format version info:
-                            final long dataVersion = raf.readLong ();
-                            
-                            if (dataVersion != IAppConstants.DATA_FORMAT_VERSION)
-                            {
-                                // read app version info for the error message:
-                                
-                                int major = 0, minor = 0, build = 0;
-                                boolean gotAppVersion = false;
-                                try
-                                {
-                                    major = raf.readInt ();
-                                    minor = raf.readInt ();
-                                    build = raf.readInt ();
-                                    
-                                    gotAppVersion = true;
-                                }
-                                catch (Throwable ignore) {}
-                                
-                                // TODO: error code here?
-                                if (gotAppVersion)
-                                {
-                                    throw new IOException ("cannot merge new data into [" + file.getAbsolutePath () + "]: created by another " + IAppConstants.APP_NAME + " version [" + makeAppVersion (major, minor, build) + "]");
-                                }
-                                else
-                                {
-                                    throw new IOException ("cannot merge new data into [" + file.getAbsolutePath () + "]: created by another " + IAppConstants.APP_NAME + " version"); 
-                                }
-                            }
-                            else
-                            {
-                                // [assertion: file header is valid and data format version is consistent]
-                                
-                                raf.seek (FILE_HEADER_LENGTH);
-                                
-                                if (length == FILE_HEADER_LENGTH)
-                                {
-                                    // no previous data entries: append 'data'
-                                    
-                                    writeEntry (log, raf, FILE_HEADER_LENGTH, data, type);
-                                }
-                                else
-                                {
-                                    // [assertion: file length > FILE_HEADER_LENGTH]
-                                    
-                                    // write 'data' starting with the first corrupt entry or the end of the file:
-                                    
-                                    long position = FILE_HEADER_LENGTH;
-                                    long entryLength;
-                                    
-                                    while (true)
-                                    {
-                                        if (trace2) log.trace2 (method, "[" + file + "]: position " + raf.getFilePointer ());
-                                        if (position >= length) break;
-                                        
-                                        entryLength = raf.readLong ();
-                                        
-                                        if ((entryLength <= 0) || (position + entryLength + ENTRY_HEADER_LENGTH > length))
-                                            break;
-                                        else
-                                        {
-                                            if (trace2) log.trace2 (method, "[" + file + "]: found valid entry of size " + entryLength);
-                                            
-                                            position += entryLength + ENTRY_HEADER_LENGTH; 
-                                            raf.seek (position);
-                                        }
-                                    }
-                                    
-                                    if (trace2) log.trace2 (method, "[" + file + "]: adding entry at position " + position);
-                                    writeEntry (log, raf, position, data, type);
-                                }
-                            }
-                        }
-                    }
-                }
-            }
-            else
-            {
-                // 'file' does not exist:
-                
-                if (trace1) log.trace1 (method, "[" + file + "]: creating a new file");
-                
-                final File parent = file.getParentFile ();
-                if (parent != null) parent.mkdirs ();
-                
-                raf = new RandomAccessFile (file, "rw");
-                
-                overwrite = true;
-            }
-            
-            
-            if (overwrite)
-            {
-                // persist starting from 0 offset:
-                
-                if ($assert.ENABLED) $assert.ASSERT (raf != null, "raf = null");
-                
-                if (truncate) raf.seek (0);
-                writeFileHeader (raf);
-                if ($assert.ENABLED) $assert.ASSERT (raf.getFilePointer () == FILE_HEADER_LENGTH, "invalid header length: " + raf.getFilePointer ());
-                
-                writeEntry (log, raf, FILE_HEADER_LENGTH, data, type);
-            }
-        }
-        finally
-        {
-            if (raf != null) try { raf.close (); } catch (Throwable ignore) {}
-            raf = null;
-        }
-        
-        if (trace1)
-        {
-            end = System.currentTimeMillis ();
-            
-            log.trace1 (method, "[" + file + "]: file processed in " + (end - start) + " ms"); 
-        }
-    }
-    
-    private static void writeFileHeader (final DataOutput out)
-        throws IOException
-    {
-        out.writeInt (MAGIC);
-        
-        out.writeLong (IAppConstants.DATA_FORMAT_VERSION);
-        
-        out.writeInt (IAppConstants.APP_MAJOR_VERSION);
-        out.writeInt (IAppConstants.APP_MINOR_VERSION);
-        out.writeInt (IAppConstants.APP_BUILD_ID);
-    }
-    
-    private static void writeEntryHeader (final DataOutput out, final byte type)
-        throws IOException
-    {
-        out.writeLong (UNKNOWN); // length placeholder
-        out.writeByte (type);
-    }
-    
-    private static void writeEntry (final Logger log, final RandomAccessFile raf, final long marker, final IMergeable data, final byte type)
-        throws IOException
-    {
-        // [unfinished] entry header:
-        writeEntryHeader (raf, type);
-        
-        // serialize 'data' starting with the current raf position:
-        RandomAccessFileOutputStream rafout = new RandomAccessFileOutputStream (raf, IO_BUF_SIZE); // note: no new file descriptors created here
-        {
-//            ObjectOutputStream oout = new ObjectOutputStream (rafout);
-//            
-//            oout.writeObject (data);
-//            oout.flush ();
-//            oout = null;
-            
-            DataOutputStream dout = new DataOutputStream (rafout);
-            switch (type)
-            {
-                case TYPE_METADATA: MetaData.writeExternal ((MetaData) data, dout);
-                    break;
-                    
-                default /* TYPE_COVERAGEDATA */: CoverageData.writeExternal ((CoverageData) data, dout);
-                    break;
-                    
-            } // end of switch
-            dout.flush ();
-            dout = null;
-            
-            // truncate:
-            raf.setLength (raf.getFilePointer ());
-        }
-
-        // transact this entry [finish the header]:
-        raf.seek (marker);
-        raf.writeLong (rafout.getCount ());
-        if (DO_FSYNC) raf.getFD ().sync ();
-        
-        if (log.atTRACE2 ()) log.trace2 ("writeEntry", "entry [" + data.getClass ().getName () + "] length: " + rafout.getCount ());
-    }
-    
-    private static IMergeable readEntry (final RandomAccessFile raf, final byte type, final long entryLength)
-        throws IOException
-    {
-        final Object data;
-        
-        RandomAccessFileInputStream rafin = new RandomAccessFileInputStream (raf, IO_BUF_SIZE); // note: no new file descriptors created here
-        {
-//           ObjectInputStream oin = new ObjectInputStream (rafin);
-//            
-//            try
-//            {
-//                data = oin.readObject ();
-//            }
-//            catch (ClassNotFoundException cnfe)
-//            {
-//                // TODO: EMMA exception here
-//                throw new IOException ("could not read data entry: " + cnfe.toString ());
-//            }
-
-            DataInputStream din = new DataInputStream (rafin);
-            switch (type)
-            {
-                case TYPE_METADATA: data = MetaData.readExternal (din);
-                    break;
-                    
-                default /* TYPE_COVERAGEDATA */: data = CoverageData.readExternal (din);
-                    break;
-                    
-            } // end of switch
-        }
-        
-        if ($assert.ENABLED) $assert.ASSERT (rafin.getCount () == entryLength, "entry length mismatch: " + rafin.getCount () + " != " + entryLength);
-        
-        return (IMergeable) data;
-    }
-    
-    
-    /*
-     * This is cloned from EMMAProperties by design, to eliminate a CONSTANT_Class_info
-     * dependency between this and EMMAProperties classes.
-     */
-    private static String makeAppVersion (final int major, final int minor, final int build)
-    {
-        final StringBuffer buf = new StringBuffer ();
-        
-        buf.append (major);
-        buf.append ('.');
-        buf.append (minor);
-        buf.append ('.');
-        buf.append (build);
-        
-        return buf.toString ();
-    }
-    
-
-    private static final int NULL_ARRAY_LENGTH = -1;
-    
-    private static final int MAGIC = 0x454D4D41; // "EMMA"
-    private static final long UNKNOWN = 0L;
-    private static final int FILE_HEADER_LENGTH = 4 + 8 + 3 * 4; // IMPORTANT: update on writeFileHeader() changes
-    private static final int ENTRY_HEADER_LENGTH = 8 + 1; // IMPORTANT: update on writeEntryHeader() changes
-    private static final boolean DO_FSYNC = true;
-    private static final int IO_BUF_SIZE = 32 * 1024;
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/emma/data/ICoverageData.java b/core/java12/com/vladium/emma/data/ICoverageData.java
deleted file mode 100644
index c7476c0..0000000
--- a/core/java12/com/vladium/emma/data/ICoverageData.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ICoverageData.java,v 1.1.1.1 2004/05/09 16:57:31 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface ICoverageData extends IMergeable
-{
-    // public: ................................................................
-    
-    final class DataHolder
-    {
-        public DataHolder (final boolean [][] coverage, final long stamp)
-        {
-            m_coverage = coverage;
-            m_stamp = stamp;
-        }
-        
-        public final boolean [][] m_coverage;
-        public final long m_stamp;
-        
-    } // end of nested class
-    
-    Object lock ();
-    
-    ICoverageData shallowCopy ();
-    
-    int size ();
-    
-    /**
-     * can return null
-     * can return data holder with a different version stamp than cls.getStamp()
-     */
-    DataHolder getCoverage (ClassDescriptor cls);
-    
-    //void setImmutable (); // TODO: this only disables addClass(), not coverage array updates; rename
-    void addClass (boolean [][] coverage, String classVMName, long stamp);
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/IMergeable.java b/core/java12/com/vladium/emma/data/IMergeable.java
deleted file mode 100644
index b484ece..0000000
--- a/core/java12/com/vladium/emma/data/IMergeable.java
+++ /dev/null
@@ -1,30 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IMergeable.java,v 1.1.1.1 2004/05/09 16:57:31 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.Serializable;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IMergeable extends Serializable
-{
-    // public: ................................................................
-    
-    boolean isEmpty ();
-    
-    /**
-     * Caller must always switch to the returned handle. 
-     */
-    IMergeable merge (IMergeable data);
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/IMetaData.java b/core/java12/com/vladium/emma/data/IMetaData.java
deleted file mode 100644
index 14fe0ce..0000000
--- a/core/java12/com/vladium/emma/data/IMetaData.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IMetaData.java,v 1.1.1.1 2004/05/09 16:57:31 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.util.Iterator;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IMetaData extends IMergeable
-{
-    // public: ................................................................
-    
-    Object lock ();
-    
-    IMetaData shallowCopy ();
-    
-    CoverageOptions getOptions ();
-    
-    int size ();
-    boolean hasSrcFileData ();
-    boolean hasLineNumberData ();
-    
-//    boolean hasDescriptor (ClassDescriptor cls);
-    boolean hasDescriptor (String classVMName);
-    
-    Iterator /* ClassDescripor */ iterator ();
-    
-    //void setImmutable (); // TODO: this only disables add(); rename
-    boolean add (ClassDescriptor cls, boolean overwrite);    
-
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/emma/data/IMetadataConstants.java b/core/java12/com/vladium/emma/data/IMetadataConstants.java
deleted file mode 100644
index 8fb537d..0000000
--- a/core/java12/com/vladium/emma/data/IMetadataConstants.java
+++ /dev/null
@@ -1,30 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IMetadataConstants.java,v 1.1.1.1 2004/05/09 16:57:31 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, 2003
- */
-public
-interface IMetadataConstants
-{
-    // public: ................................................................
-    
-    int METHOD_NO_LINE_NUMBER_TABLE = 0x01;
-    int METHOD_ABSTRACT_OR_NATIVE   = 0x02;
-    int METHOD_EXCLUDED             = 0x04;
-    int METHOD_ADDED                = 0x08;
-    
-    int METHOD_NO_BLOCK_DATA = (METHOD_ABSTRACT_OR_NATIVE | METHOD_EXCLUDED | METHOD_ADDED);
-    int METHOD_NO_LINE_DATA = (METHOD_NO_LINE_NUMBER_TABLE | METHOD_NO_BLOCK_DATA);
-    
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/ISessionData.java b/core/java12/com/vladium/emma/data/ISessionData.java
deleted file mode 100644
index a216497..0000000
--- a/core/java12/com/vladium/emma/data/ISessionData.java
+++ /dev/null
@@ -1,24 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ISessionData.java,v 1.1.1.1 2004/05/09 16:57:32 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface ISessionData
-{
-    // public: ................................................................
-    
-    IMetaData getMetaData ();
-    ICoverageData getCoverageData ();
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/MergeProcessor.java b/core/java12/com/vladium/emma/data/MergeProcessor.java
deleted file mode 100644
index dbae3d0..0000000
--- a/core/java12/com/vladium/emma/data/MergeProcessor.java
+++ /dev/null
@@ -1,368 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: MergeProcessor.java,v 1.1.1.1.2.2 2004/07/16 23:32:29 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.File;
-import java.io.IOException;
-
-import com.vladium.logging.Logger;
-import com.vladium.util.Files;
-import com.vladium.util.IConstants;
-import com.vladium.util.IProperties;
-import com.vladium.util.asserts.$assert;
-import com.vladium.util.exception.Exceptions;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMAProperties;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.Processor;
-
-// ----------------------------------------------------------------------------
-/*
- * This class was not meant to be public by design. It is made to to work around
- * access bugs in reflective invocations. 
- */
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class MergeProcessor extends Processor
-                           implements IAppErrorCodes
-{
-    // public: ................................................................
-    
-    public static MergeProcessor create ()
-    {
-        return new MergeProcessor ();
-    }
-
-    /**
-     * 
-     * @param path [null is equivalent to an empty array]
-     */
-    public synchronized final void setDataPath (final String [] path)
-    {
-        if ((path == null) || (path.length == 0))
-            m_dataPath = IConstants.EMPTY_FILE_ARRAY;
-        else
-            m_dataPath = Files.pathToFiles (path, true);
-    }
-    
-    /**
-     * NOTE: there is no setter for merge attribute because this processor
-     * always overwrites the out file [to ensure compaction]
-     * 
-     * @param fileName [null unsets the previous override setting]
-     */
-    public synchronized final void setSessionOutFile (final String fileName)
-    {
-        if (fileName == null)
-            m_sdataOutFile = null;
-        else
-        {
-            final File _file = new File (fileName);
-                
-            if (_file.exists () && ! _file.isFile ())
-                throw new IllegalArgumentException ("not a file: [" + _file.getAbsolutePath () + "]");
-                
-            m_sdataOutFile = _file;
-        }
-    }
-    
-    // protected: .............................................................
-
-    
-    protected void validateState ()
-    {
-        super.validateState ();
-        
-        if (m_dataPath == null)
-            throw new IllegalStateException ("data path not set");
-        
-        // [m_sdataOutFile can be null]
-        
-        // [m_propertyOverrides can be null]
-    }
-    
-    
-    protected void _run (final IProperties toolProperties)
-    {
-        final Logger log = m_log;
-
-        final boolean verbose = m_log.atVERBOSE ();
-        if (verbose)
-        {
-            log.verbose (IAppConstants.APP_VERBOSE_BUILD_ID);
-            
-            // [assertion: m_dataPath != null]
-            log.verbose ("input data path:");
-            log.verbose ("{");
-            for (int p = 0; p < m_dataPath.length; ++ p)
-            {
-                final File f = m_dataPath [p];
-                final String nonexistent = f.exists () ? "" : "{nonexistent} ";
-                
-                log.verbose ("  " + nonexistent + f.getAbsolutePath ());
-            }
-            log.verbose ("}");
-        }
-        else
-        {
-            log.info ("processing input files ...");
-        }
-        
-        // get the data out settings:
-        File sdataOutFile = m_sdataOutFile;
-        {
-            if (sdataOutFile == null)
-                sdataOutFile = new File (toolProperties.getProperty (EMMAProperties.PROPERTY_SESSION_DATA_OUT_FILE,
-                                                                     EMMAProperties.DEFAULT_SESSION_DATA_OUT_FILE));
-        }
-                
-        RuntimeException failure = null;
-        try
-        {
-            IMetaData mdata = null;
-            ICoverageData cdata = null;
-            
-            // merge all data files:
-            try
-            {
-                final long start = log.atINFO () ? System.currentTimeMillis () : 0;
-                
-                for (int f = 0; f < m_dataPath.length; ++ f)
-                {
-                    final File dataFile = m_dataPath [f];
-                    if (verbose) log.verbose ("processing input file [" + dataFile.getAbsolutePath () + "] ...");
-                    
-                    final IMergeable [] fileData = DataFactory.load (dataFile);
-                    
-                    final IMetaData _mdata = (IMetaData) fileData [DataFactory.TYPE_METADATA];
-                    if (_mdata != null)
-                    {
-                        if (verbose) log.verbose ("  loaded " + _mdata.size () + " metadata entries");
-                        
-                        if (mdata == null)
-                            mdata = _mdata;
-                        else
-                            mdata = (IMetaData) mdata.merge (_mdata); // note: later datapath entries override earlier ones
-                    }
-                    
-                    final ICoverageData _cdata = (ICoverageData) fileData [DataFactory.TYPE_COVERAGEDATA];
-                    if (_cdata != null)
-                    {
-                        if (verbose) log.verbose ("  loaded " + _cdata.size () + " coverage data entries");
-                        
-                        if (cdata == null)
-                            cdata = _cdata;
-                        else
-                            cdata = (ICoverageData) cdata.merge (_cdata); // note: later datapath entries override earlier ones
-                    }
-                    
-                    ++ m_dataFileCount;
-                }
-                
-                if (log.atINFO ())
-                {
-                    final long end = System.currentTimeMillis ();
-                    
-                    log.info (m_dataFileCount + " file(s) read and merged in " + (end - start) + " ms");
-                }
-                
-                if (((mdata == null) || mdata.isEmpty ()) && ((cdata == null) || cdata.isEmpty ()))
-                {
-                    log.warning ("nothing to do: no metadata or coverage data found in any of the input files");
-                    
-                    // TODO: throw exception or exit quietly?
-                    return;
-                }
-            }
-            catch (IOException ioe)
-            {
-                // TODO: handle
-                ioe.printStackTrace (System.out);
-            }
-            
-
-            if (verbose)
-            {
-                if (mdata != null)
-                {
-                    log.verbose ("  merged metadata contains " + mdata.size () + " entries");
-                }
-                
-                if (cdata != null)
-                {
-                    log.verbose ("  merged coverage data contains " + cdata.size () + " entries");
-                }
-            }
-            
-            // write merged data into output file:
-            {
-                $assert.ASSERT (sdataOutFile != null, "sdataOutFile not null");
-                    
-                // the case of the output file being one of the input files is
-                // supported; however, for safety reasons we create output in
-                // a temp file and rename it only when the data is safely persisted:
-                
-                boolean rename = false;
-                File tempDataOutFile = null;
-                
-                final File canonicalDataOutFile = Files.canonicalizeFile (sdataOutFile);
-                
-                for (int f = 0; f < m_dataPath.length; ++ f)
-                {
-                    final File canonicalDataFile = Files.canonicalizeFile (m_dataPath [f]);
-                    if (canonicalDataOutFile.equals (canonicalDataFile))
-                    {
-                        rename = true;
-                        break;
-                    }
-                }
-                
-                if (rename) // create a temp out file
-                {
-                    File tempFileDir = canonicalDataOutFile.getParentFile ();
-                    if (tempFileDir == null) tempFileDir = new File ("");
-                    
-                    // length > 3:
-                    final String tempFileName = Files.getFileName (canonicalDataOutFile) + IAppConstants.APP_NAME_LC;
-                    final String tempFileExt = EMMAProperties.PROPERTY_TEMP_FILE_EXT;
-                
-                    try
-                    {
-                        tempDataOutFile = Files.createTempFile (tempFileDir, tempFileName, tempFileExt);
-                    }
-                    catch (IOException ioe)
-                    {
-                        // TODO: error code
-                        throw new EMMARuntimeException (ioe);
-                    }
-                    
-                    log.warning ("the specified output file is one of the input files [" + canonicalDataOutFile + "]");
-                    log.warning ("all merged data will be written to a temp file first [" + tempDataOutFile.getAbsolutePath ()  + "]");
-                }
-                
-                // persist merged session data:
-                {
-                    final long start = log.atINFO () ? System.currentTimeMillis () : 0;
-                    
-                    File persistFile = null;
-                    try
-                    {
-                        persistFile = tempDataOutFile != null ? tempDataOutFile : canonicalDataOutFile;
-                        
-                        // TODO: the persister API is ugly, redesign
-                        
-                        if ((mdata == null) || mdata.isEmpty ())
-                            DataFactory.persist (cdata, persistFile, false); // never merge to enforce compaction behavior
-                        else if ((cdata == null) || cdata.isEmpty ())
-                            DataFactory.persist (mdata, persistFile, false); // never merge to enforce compaction behavior
-                        else
-                            DataFactory.persist (new SessionData (mdata, cdata), persistFile, false); // never merge to enforce compaction behavior
-                    }
-                    catch (IOException ioe)
-                    {
-                        if (persistFile != null) persistFile.delete ();
-                        
-                        // TODO: error code
-                        throw new EMMARuntimeException (ioe);
-                    }
-                    catch (Error e)
-                    {
-                        if (persistFile != null) persistFile.delete ();
-                        
-                        throw e; // re-throw
-                    }
-                    
-                    if (rename) // rename-with-delete temp out file into the desired out file
-                    {
-                        if (! Files.renameFile (tempDataOutFile, canonicalDataOutFile, true)) // overwrite the original archive
-                        {
-                            // error code
-                            throw new EMMARuntimeException ("could not rename temporary file [" + tempDataOutFile.getAbsolutePath () + "] to [" + canonicalDataOutFile + "]: make sure the original file is not locked and can be deleted");
-                        }
-                    }
-                    
-                    if (log.atINFO ())
-                    {
-                        final long end = System.currentTimeMillis ();
-                        
-                        log.info ("merged/compacted data written to [" + canonicalDataOutFile + "] {in " + (end - start) + " ms}");
-                    }
-                }
-            }            
-        }
-        catch (SecurityException se)
-        {
-            failure = new EMMARuntimeException (SECURITY_RESTRICTION, new String [] {IAppConstants.APP_NAME}, se);
-        }
-        catch (RuntimeException re)
-        {
-            failure = re;
-        }
-        finally
-        {
-            reset ();
-        }
-        
-        if (failure != null)
-        {
-            if (Exceptions.unexpectedFailure (failure, EXPECTED_FAILURES))
-            {
-                throw new EMMARuntimeException (UNEXPECTED_FAILURE,
-                                                new Object [] {failure.toString (), IAppConstants.APP_BUG_REPORT_LINK},
-                                                failure);
-            }
-            else
-                throw failure;
-        }
-    }
-
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private MergeProcessor ()
-    {
-        m_dataPath = IConstants.EMPTY_FILE_ARRAY;
-    }
-    
-    
-    private void reset ()
-    {
-        m_dataFileCount = 0;
-    }
-    
-    
-    // caller-settable state [scoped to this runner instance]:
-    
-    private File [] m_dataPath; // required to be non-null for run() [is set to canonicalized form]
-    private File m_sdataOutFile; // user override; can be null for run()
-
-    // internal run()-scoped state:
-    
-    private int m_dataFileCount;
-    
-    private static final Class [] EXPECTED_FAILURES; // set in <clinit>
-    
-    static
-    {
-        EXPECTED_FAILURES = new Class []
-        {
-            EMMARuntimeException.class,
-            IllegalArgumentException.class,
-            IllegalStateException.class,
-        };
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/MetaData.java b/core/java12/com/vladium/emma/data/MetaData.java
deleted file mode 100644
index 5416f8a..0000000
--- a/core/java12/com/vladium/emma/data/MetaData.java
+++ /dev/null
@@ -1,289 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: MetaData.java,v 1.1.1.1.2.2 2004/07/16 23:32:29 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.DataInput;
-import java.io.DataOutput;
-import java.io.IOException;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.Map;
-
-import com.vladium.logging.Logger;
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/*
- * Average mem size/class entry: 6166 bytes [1.4.1, rt.jar], 5764 bytes [1.3.1, rt.jar]
- */
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-final class MetaData implements IMetaData, Cloneable
-{
-    // public: ................................................................
-    
-    // TODO: MT-safety model
-    
-    // TODO: no duplicate detection is done here at the moment
-    // [may require supporting fast lookup for already added descriptors]
-    
-    public IMetaData shallowCopy ()
-    {
-        final MetaData _clone;
-        try
-        {
-            _clone = (MetaData) super.clone ();
-        }
-        catch (CloneNotSupportedException cnse)
-        {
-            throw new Error (cnse.toString ());
-        }
-        
-        final HashMap _classMap;
-        
-        synchronized (lock ())
-        {
-            _classMap = (HashMap) m_classMap.clone ();
-        }
-        
-        // [m_packagesWarned is not cloned by design]
-        
-        _clone.m_classMap = _classMap;
-        
-        return _clone;  
-    }
-    
-    public CoverageOptions getOptions ()
-    {
-        return m_options;
-    }
-    
-    public int size ()
-    {
-        return m_classMap.size (); 
-    }
-    
-    public boolean hasSrcFileData ()
-    {
-        return m_hasSrcFileInfo;
-    }
-    
-    public boolean hasLineNumberData ()
-    {
-        return m_hasLineNumberInfo;
-    }
-    
-    public Iterator iterator ()
-    {
-        return m_classMap.values ().iterator ();
-    }
-    
-//    public boolean hasDescriptor (final ClassDescriptor cls)
-//    {
-//        if ($assert.ENABLED) $assert.ASSERT (cls != null, "cls is null");
-//        
-//        return m_classes.contains (cls);
-//    }
-
-    public boolean hasDescriptor (final String classVMName)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (classVMName != null, "className is null");
-        
-        return m_classMap.containsKey (classVMName);
-    }
-    
-    public Object lock ()
-    {
-        return m_classMap;
-    }
-        
-    public boolean add (final ClassDescriptor cls, final boolean overwrite)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (cls != null, "cls is null");
-        
-        final String classVMName = cls.getClassVMName ();
-        
-        if (overwrite || ! m_classMap.containsKey (classVMName))
-        {
-            m_classMap.put (classVMName, cls);
-            
-            boolean incompleteDebugInfo = false;
-
-            if (! cls.hasSrcFileInfo ())
-            {
-                m_hasSrcFileInfo = false;
-                incompleteDebugInfo = true;
-            }
-            
-            if (! cls.hasCompleteLineNumberInfo ())
-            {
-                m_hasLineNumberInfo = false;
-                incompleteDebugInfo = true;
-            }
-            
-            // SF FR 971176: provide user with sample classes that may later
-            // caused warnings about line coverage not available
-            
-            if (incompleteDebugInfo)
-            {
-                final Logger log = Logger.getLogger ();
-                
-                if (log.atINFO ())
-                {
-                    final String packageVMName = cls.getPackageVMName ();
-                    
-                    if (m_packagesWarned.add (packageVMName))
-                    {
-                        log.info ("package [" + packageVMName + "] contains classes [" + cls.getName () + "] without full debug info");
-                    }
-                }
-            }
-            
-            return true;
-        }
-
-        return false;
-    }
-    
-    // IMergeable:
-    
-    public boolean isEmpty ()
-    {
-        return m_classMap.isEmpty ();
-    }
-    
-    /*
-     * note: rhs entries must override current entries
-     */
-    public IMergeable merge (final IMergeable rhs)
-    {
-        if ((rhs == null) || rhs.isEmpty () || (rhs == this))
-            return this;
-        else
-        {
-            final MetaData rhsmdata = (MetaData) rhs; // TODO: redesign to avoid this cast?
-            final Map rhsclasses = rhsmdata.m_classMap;
-            
-            // rhs entries always override existing content:
-            
-            for (Iterator entries = rhsclasses.entrySet ().iterator (); entries.hasNext (); )
-            {
-                final Map.Entry entry = (Map.Entry) entries.next ();
-                
-                final String classVMName = (String) entry.getKey ();
-                final Object rhsdescriptor = entry.getValue ();
-                    
-                m_classMap.put (classVMName, rhsdescriptor);
-            }
-            
-            // update debug info flags if necessary:
-            
-            if (! rhsmdata.hasSrcFileData ()) m_hasSrcFileInfo = false;
-            if (! rhsmdata.hasLineNumberData ()) m_hasLineNumberInfo = false;
-                
-            return this;
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    MetaData (final CoverageOptions options)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (options != null, "options is null");
-        m_options = options;
-        
-        m_hasSrcFileInfo = true;
-        m_hasLineNumberInfo = true;
-        
-        m_classMap = new HashMap ();
-        m_packagesWarned = new HashSet ();
-    }
-    
-    
-    static MetaData readExternal (final DataInput in)
-        throws IOException
-    {
-        final CoverageOptions options = CoverageOptions.readExternal (in);
-        
-        final boolean hasSrcFileInfo = in.readBoolean ();
-        final boolean hasLineNumberInfo = in.readBoolean ();
-        
-        final int size = in.readInt ();
-        final HashMap classMap = new HashMap (size);
-        
-        for (int i = 0; i < size; ++ i)
-        {
-            final String classVMName = in.readUTF ();
-            final ClassDescriptor cls = ClassDescriptor.readExternal (in);
-            
-            classMap.put (classVMName, cls);
-        }
-        
-        // [m_packagesWarned is not part of persisted state]
-        
-        return new MetaData (options, classMap, hasSrcFileInfo, hasLineNumberInfo);
-    }
-    
-    static void writeExternal (final MetaData mdata, final DataOutput out)
-        throws IOException
-    {
-        CoverageOptions.writeExternal (mdata.m_options, out);
-        
-        out.writeBoolean (mdata.m_hasSrcFileInfo);
-        out.writeBoolean (mdata.m_hasLineNumberInfo);
-        
-        final Map classMap = mdata.m_classMap;
-        
-        final int size = classMap.size ();
-        out.writeInt (size); // too bad the capacity is not visible
-        
-        final Iterator entries = classMap.entrySet ().iterator ();
-        for (int i = 0; i < size; ++ i)
-        {
-            final Map.Entry entry = (Map.Entry) entries.next ();
-            
-            final String classVMName = (String) entry.getKey ();
-            final ClassDescriptor cls = (ClassDescriptor) entry.getValue ();
-            
-            out.writeUTF (classVMName);
-            ClassDescriptor.writeExternal (cls, out);
-        }
-        
-        // [m_packagesWarned is not part of persisted state]
-    }
-    
-    // private: ...............................................................
-    
-    
-    private MetaData (final CoverageOptions options, final HashMap classMap,
-                      final boolean hasSrcFileInfo, final boolean hasLineNumberInfo)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (options != null, "options is null");
-        m_options = options;
-        
-        m_hasSrcFileInfo = hasSrcFileInfo;
-        m_hasLineNumberInfo = hasLineNumberInfo;
-        
-        m_classMap = classMap;
-    }
-    
-    
-    private final CoverageOptions m_options; // [never null]
-    private boolean m_hasSrcFileInfo, m_hasLineNumberInfo;
-    private /*final*/ HashMap /* classVMName:String->ClassDescriptor */ m_classMap; // [never null]
-    
-    private /*final*/ transient HashSet /*  packageVMName:String */ m_packagesWarned; // [never null]
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/MethodDescriptor.java b/core/java12/com/vladium/emma/data/MethodDescriptor.java
deleted file mode 100644
index ac6cd25..0000000
--- a/core/java12/com/vladium/emma/data/MethodDescriptor.java
+++ /dev/null
@@ -1,327 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: MethodDescriptor.java,v 1.1.1.1.2.1 2004/07/10 03:34:52 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.DataInput;
-import java.io.DataOutput;
-import java.io.IOException;
-import java.io.Serializable;
-
-import com.vladium.util.IConstants;
-import com.vladium.util.IntObjectMap;
-import com.vladium.util.IntSet;
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class MethodDescriptor implements IConstants, IMetadataConstants, Serializable
-{
-    // public: ................................................................    
-    
-    // need a separate 'blockCount' parm because 'blockMap' could be null
-    // and for a class that is never loaded I can't find out the number of
-    // blocks for block coverage reporting
-
-    public MethodDescriptor (final String name, final String descriptor, final int status,
-                             final int [] blockSizes, final int [][] blockMap, final int firstLine)
-    {
-        if (name == null)
-            throw new IllegalArgumentException ("null input: name");
-        if (descriptor == null)
-            throw new IllegalArgumentException ("null input: descriptor");
-        
-        if ((status & METHOD_NO_BLOCK_DATA) == 0)
-        {
-            // block metadata is available: blockCount must be positive
-            
-            final int blockCount = blockSizes.length;
-            
-            if ($assert.ENABLED) $assert.ASSERT (blockCount > 0, "blockCount must be positive: " + blockCount);
-            m_blockSizes = blockSizes;
-            
-            if ((status & METHOD_NO_LINE_DATA) == 0)
-            {
-                // line metadata is available: blockMap must not be null or empty
-                
-                if ($assert.ENABLED) $assert.ASSERT (firstLine > 0, "firstLine must be positive: " + firstLine);
-                
-                if ((blockMap == null) || (blockMap.length == 0))
-                    throw new IllegalArgumentException ("null or empty input: blockMap");
-            
-                if ($assert.ENABLED)
-                {
-                    $assert.ASSERT (blockCount == blockMap.length, "blockCount " + blockCount + " != blockMap.length " + blockMap.length);
-                    
-                    for (int i = 0; i < blockMap.length; ++ i)
-                    {
-                        $assert.ASSERT (blockMap [i] != null, "blockMap[" + i + "] is null");
-                        // note: it is legal for blockMap [i] to be empty
-                    }
-                }
-                
-                m_blockMap = blockMap;
-                m_firstLine = firstLine;
-            }
-            else
-            {
-                m_blockMap = null;
-                m_firstLine = 0;
-            }
-        }
-        else
-        {
-            m_blockSizes = null;
-            m_blockMap = null;
-            m_firstLine = 0;
-        }
-        
-        m_name = name;
-        m_descriptor = descriptor;
-        m_status = status;
-    }
-    
-    
-    public String getName ()
-    {
-        return m_name;
-    }
-    
-    public String getDescriptor ()
-    {
-        return m_descriptor;
-    }
-    
-    public int getStatus ()
-    {
-        return m_status;
-    }
-    
-    public int getBlockCount ()
-    {
-        return m_blockSizes.length;
-    }
-
-    public int [] getBlockSizes ()
-    {
-        return m_blockSizes;
-    }
-
-    public int [][] getBlockMap ()
-    {
-        return m_blockMap;
-    }
-    
-    public IntObjectMap /* line no->int[](blockIDs) */ getLineMap ()
-    {
-        IntObjectMap lineMap = m_lineMap;
-        if (lineMap != null)
-            return lineMap;
-        else if ((m_status & METHOD_NO_LINE_DATA) == 0)
-        {
-            // construct reverse line->block ID mapping:
-            
-            lineMap = new IntObjectMap ();
-            final int [][] blockMap = m_blockMap;
-            
-            for (int bl = 0, blCount = blockMap.length; bl < blCount; ++ bl)
-            {
-                final int [] lines = blockMap [bl];
-                if (lines != null)
-                {
-                    final int lineCount = lines.length;
-                    
-                    for (int l = 0; l < lineCount; ++ l)
-                    {
-                        final int line = lines [l];
-                        IntSet blockIDs = (IntSet) lineMap.get (line);
-                        
-                        if (blockIDs == null)
-                        {
-                            blockIDs = new IntSet ();
-                            lineMap.put (line, blockIDs);
-                        }
-                        
-                        blockIDs.add (bl);
-                    }
-                }
-            }
-            
-            final int [] lines = lineMap.keys ();
-            for (int l = 0, lineCount = lines.length; l < lineCount; ++ l)
-            {
-                final int line = lines [l];
-                final int [] blockIDs = ((IntSet) lineMap.get (line)).values ();
-                if ($assert.ENABLED) $assert.ASSERT (blockIDs != null && blockIDs.length > 0, "wrong line mapping for line #" + line);
-                
-                lineMap.put (line, blockIDs); // overwrite IntSet as the value
-            }
-            
-            m_lineMap = lineMap;
-            
-            return lineMap;
-        }
-        
-        return null;
-    }
-    
-    public int getFirstLine ()
-    {
-        return m_firstLine;
-    }
-    
-    public boolean hasLineNumberInfo ()
-    {
-        return (m_status & METHOD_NO_LINE_DATA) == 0;
-    }
-    
-    
-    public String toString ()
-    {
-        return toString ("");
-    }
-    
-    public String toString (final String indent)
-    {
-        StringBuffer s = new StringBuffer (indent + "method [" + m_name + "] descriptor:");
-        
-        if ((m_status & METHOD_NO_LINE_DATA) == 0)
-        {
-            for (int bl = 0; bl < m_blockMap.length; ++ bl)
-            {
-                s.append (EOL);
-                s.append (indent + INDENT_INCREMENT + "block " + bl + " (" + m_blockSizes [bl] + " instrs) : ");
-                
-                final int [] lines = m_blockMap [bl];
-                for (int l = 0; l < lines.length; ++ l)
-                {
-                    if (l != 0) s.append (", ");
-                    s.append (lines [l]);
-                }
-            }
-            s.append (EOL);
-            s.append (indent + INDENT_INCREMENT + "---");
-            
-            final int [] lines = m_lineMap.keys ();
-            for (int l = 0; l < lines.length; ++ l)
-            {
-                s.append (EOL);
-                s.append (indent + INDENT_INCREMENT + "line " + lines [l] + ": ");
-                
-                final int [] blocks = (int []) m_lineMap.get (lines [l]);
-                for (int bl = 0; bl < blocks.length; ++ bl)
-                {
-                    if (bl != 0) s.append (", ");
-                    s.append (blocks [bl]);
-                }
-            }
-        }
-        else
-        {
-            s.append (" <no line info>");
-        }
-        
-        return s.toString ();
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    static MethodDescriptor readExternal (final DataInput in)
-        throws IOException
-    {
-        final String name = in.readUTF ();
-        final String descriptor = in.readUTF ();
-        
-        final int status = in.readInt ();
-        
-        int [] blockSizes = null;
-        int [][] blockMap = null;
-        int firstLine = 0;
-        
-        if ((status & METHOD_NO_BLOCK_DATA) == 0)
-        {
-            // blockSizes must be set:
-            
-            blockSizes = DataFactory.readIntArray (in);
-            
-            if ((status & METHOD_NO_LINE_DATA) == 0)
-            {
-                // blockMap, lineMap, firstLine must be set:
-                
-                final int length = in.readInt ();
-                blockMap = new int [length][];
-                
-                for (int i = 0; i < length; ++ i) 
-                {
-                    blockMap [i] = DataFactory.readIntArray (in);
-                }
-                
-                firstLine = in.readInt ();
-                
-                // [lineMap is transient data]
-            }
-        }
-        
-        return new MethodDescriptor (name, descriptor, status, blockSizes, blockMap, firstLine);
-    }
-    
-    static void writeExternal (final MethodDescriptor method, final DataOutput out)
-        throws IOException
-    {
-        out.writeUTF (method.m_name);
-        out.writeUTF (method.m_descriptor);
-        
-        final int status = method.m_status;
-        out.writeInt (status);
-        
-        if ((status & METHOD_NO_BLOCK_DATA) == 0)
-        {
-            // blockSizes must be set:
-            
-            DataFactory.writeIntArray (method.m_blockSizes, out);
-            
-            if ((status & METHOD_NO_LINE_DATA) == 0)
-            {
-                // blockMap, lineMap, firstLine must be set:
-                
-                final int [][] blockMap = method.m_blockMap;
-                final int length = blockMap.length;
-                out.writeInt (length);
-
-                for (int i = 0; i < length; ++ i) 
-                {
-                    DataFactory.writeIntArray (blockMap [i], out);
-                }
-                
-                out.writeInt (method.m_firstLine);
-                
-                // [lineMap is transient data]
-            }
-        }
-    }
-    
-    // private: ...............................................................
-    
-    
-    private final String m_name; // internal JVM name (<init>, <clinit> for initializers, etc) [never null]
-    private final String m_descriptor; // [never null]
-    private final int m_status; // excluded, no debug data, etc
-    private final int [] m_blockSizes; // always of positive length if ((status & METHOD_NO_BLOCK_DATA) == 0)
-    private final int [][] m_blockMap; // [never null or empty if status is ...]
-    private final int m_firstLine; // 0 if not src line info is available
-    
-    private IntObjectMap /* line no->int[](blockIDs) */  m_lineMap; // created lazily [could be empty if status ...]
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/emma/data/SessionData.java b/core/java12/com/vladium/emma/data/SessionData.java
deleted file mode 100644
index e7b584a..0000000
--- a/core/java12/com/vladium/emma/data/SessionData.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: SessionData.java,v 1.1.1.1 2004/05/09 16:57:33 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.Serializable;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class SessionData implements ISessionData, Serializable 
-{
-    // public: ................................................................
-    
-    public IMetaData getMetaData ()
-    {
-        return m_mdata;
-    }
-    
-    public ICoverageData getCoverageData ()
-    {
-        return m_cdata;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    public SessionData (final IMetaData mdata, final ICoverageData cdata)
-    {
-        if (mdata == null) throw new IllegalArgumentException ("null input: mdata");
-        if (cdata == null) throw new IllegalArgumentException ("null input: cdata");
-        
-        m_mdata = mdata;
-        m_cdata = cdata;
-    }
-    
-    // private: ...............................................................
-    
-    
-    private final IMetaData m_mdata;
-    private final ICoverageData m_cdata;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/data/mergeCommand.java b/core/java12/com/vladium/emma/data/mergeCommand.java
deleted file mode 100644
index 5a98c23..0000000
--- a/core/java12/com/vladium/emma/data/mergeCommand.java
+++ /dev/null
@@ -1,166 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: mergeCommand.java,v 1.1.1.1.2.1 2004/07/16 23:32:29 vlad_r Exp $
- */
-package com.vladium.emma.data;
-
-import java.io.IOException;
-
-import com.vladium.util.ClassLoaderResolver;
-import com.vladium.util.args.IOptsParser;
-import com.vladium.emma.Command;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMARuntimeException;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class mergeCommand extends Command
-{
-    // public: ................................................................
-
-    public mergeCommand (final String usageToolName, final String [] args)
-    {
-        super (usageToolName, args);
-    }
-
-    public synchronized void run ()
-    {
-        ClassLoader loader;
-        try
-        {
-            loader = ClassLoaderResolver.getClassLoader ();
-        }
-        catch (Throwable t)
-        {
-            loader = getClass ().getClassLoader ();
-        }
-        
-        try
-        {
-            // process 'args':
-            {
-                final IOptsParser parser = getOptParser (loader);
-                final IOptsParser.IOpts parsedopts = parser.parse (m_args);
-                
-                // check if usage is requested before checking args parse errors etc:
-                {
-                    final int usageRequestLevel = parsedopts.usageRequestLevel ();
-
-                    if (usageRequestLevel > 0)
-                    {
-                        usageexit (parser, usageRequestLevel, null);
-                        return;
-                    }
-                }
-                
-                final IOptsParser.IOpt [] opts = parsedopts.getOpts ();
-                
-                if (opts == null) // this means there were args parsing errors
-                {
-                    parsedopts.error (m_out, STDOUT_WIDTH);
-                    usageexit (parser, IOptsParser.SHORT_USAGE, null);
-                    return;
-                }
-                
-                // process parsed args:
-
-                try
-                {
-                    for (int o = 0; o < opts.length; ++ o)
-                    {
-                        final IOptsParser.IOpt opt = opts [o];
-                        final String on = opt.getCanonicalName ();
-                        
-                        if (! processOpt (opt))
-                        {
-                            if ("in".equals (on))
-                            {
-                                m_datapath = getListOptValue (opt, PATH_DELIMITERS, true);
-                            }
-                            else if ("out".equals (on))
-                            {
-                                m_outFileName = opt.getFirstValue ();
-                            }
-                        }
-                    }
-                    
-                    // user '-props' file property overrides:
-                    
-                    if (! processFilePropertyOverrides ()) return;
-                    
-                    // process prefixed opts:
-                    
-                    processCmdPropertyOverrides (parsedopts);
-                }
-                catch (IOException ioe)
-                {
-                    throw new EMMARuntimeException (IAppErrorCodes.ARGS_IO_FAILURE, ioe);
-                }
-                
-                // handle cmd line-level defaults:
-                {
-                }
-            }
-            
-            // run the reporter:
-            {
-                final MergeProcessor processor = MergeProcessor.create ();
-                processor.setAppName (IAppConstants.APP_NAME); // for log prefixing
-                
-                processor.setDataPath (m_datapath);
-                processor.setSessionOutFile (m_outFileName);
-                processor.setPropertyOverrides (m_propertyOverrides);
-                
-                processor.run ();
-            }
-        }
-        catch (EMMARuntimeException yre)
-        {
-            // TODO: see below
-            
-            exit (true, yre.getMessage (), yre, RC_UNEXPECTED); // does not return
-            return;
-        }
-        catch (Throwable t)
-        {
-            // TODO: embed: OS/JVM fingerprint, build #, etc
-            // TODO: save stack trace in a file and prompt user to send it to ...
-            
-            exit (true, "unexpected failure: ", t, RC_UNEXPECTED); // does not return
-            return;
-        }
-
-        exit (false, null, null, RC_OK);
-    }    
-    
-    // protected: .............................................................
-
-
-    protected void initialize ()
-    {
-        super.initialize ();                
-    }
-    
-    protected String usageArgsMsg ()
-    {
-        return "[options]";
-    }
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private String [] m_datapath; // list of data files, not a real path
-    private String m_outFileName;
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/filter/IInclExclFilter.java b/core/java12/com/vladium/emma/filter/IInclExclFilter.java
deleted file mode 100644
index e366c23..0000000
--- a/core/java12/com/vladium/emma/filter/IInclExclFilter.java
+++ /dev/null
@@ -1,222 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IInclExclFilter.java,v 1.1.1.1 2004/05/09 16:57:33 vlad_r Exp $
- */
-package com.vladium.emma.filter;
-
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-import java.util.StringTokenizer;
-
-import com.vladium.util.WCMatcher;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, 2003
- */
-public
-interface IInclExclFilter
-{
-    // public: ................................................................
-    
-    // TODO: move this into util pkg
-    
-    char INCLUSION_PREFIX = '+';
-    String INCLUSION_PREFIX_STRING = "+";
-    char EXCLUSION_PREFIX = '-';
-    String EXCLUSION_PREFIX_STRING = "-";
-
-    boolean included (final String s);
-
-    abstract class Factory
-    {
-        public static IInclExclFilter create (final String specs1, final String separators, final String [] specs2)
-        {
-            if ((specs1 == null) || (specs1.trim ().length () == 0))
-                return create (specs2);
-            else
-            {
-                final List /* String */ _specs = new ArrayList ();
-                
-                if (specs2 != null)
-                {
-                    for (int s = 0; s < specs2.length; ++ s)
-                    {
-                        _specs.add (specs2 [s]);
-                    }
-                }
-                
-                for (StringTokenizer tokenizer = new StringTokenizer (specs1, separators);
-                     tokenizer.hasMoreTokens (); )
-                {
-                    _specs.add (tokenizer.nextToken ());
-                }
-                
-                final String [] specs = new String [_specs.size ()];
-                _specs.toArray (specs);
-                
-                return create (specs);
-            }
-        }
-        
-        public static IInclExclFilter create (final String [] specs)
-        {
-            if ((specs == null) || (specs.length == 0))
-                return new WCInclExclFilter ((String []) null, (String []) null);
-            
-            final List inclusions = new ArrayList ();
-            final List exclusions = new ArrayList ();
-            
-            for (int i = 0, iLimit = specs.length; i < iLimit; ++ i)
-            {
-                final String spec = specs [i];
-                
-                if (spec.length () > 0)
-                {
-                    if (spec.charAt (0) == EXCLUSION_PREFIX)
-                        exclusions.add (spec.substring (1));
-                    else
-                    {
-                        // [inclusion prefix is optional]
-                        
-                        if (spec.charAt (0) == INCLUSION_PREFIX)
-                            inclusions.add (spec.substring (1));
-                        else
-                            inclusions.add (spec);
-                    }
-                } 
-            }
-            
-            return new WCInclExclFilter (inclusions, exclusions);
-        }
-        
-        public static IInclExclFilter create (final String [] inclusions,
-                                              final String [] exclusions)
-        {
-            return new WCInclExclFilter (inclusions, exclusions);
-        }
-        
-        public static IInclExclFilter create (final List /* String */ inclusions,
-                                              final List /* String */ exclusions)
-        {
-            return new WCInclExclFilter (inclusions, exclusions);
-        }
-
-        private static final class WCInclExclFilter implements IInclExclFilter
-        {
-            public boolean included (final String s)
-            {
-                if (s == null) return false;
-                
-                final char [] chars = s.toCharArray ();
-                
-                // included set is (inclusions - exclusions), where null inclusions
-                // mean 'everything' and null exclusions mean 'nothing':
-                
-                final WCMatcher [] inclusions = m_inclusions;
-                final WCMatcher [] exclusions = m_exclusions;
-                
-                if (inclusions != null)
-                {
-                    boolean included = false;
-                    
-                    for (int i = 0, iLimit = inclusions.length; i < iLimit; ++ i)
-                    {
-                        if (inclusions [i].matches (chars))
-                        {
-                            included = true;
-                            break;
-                        }
-                    }
-                    
-                    if (! included) return false;
-                }
-    
-                if (exclusions != null)
-                {
-                    for (int x = 0, xLimit = exclusions.length; x < xLimit; ++ x)
-                    {
-                        if (exclusions [x].matches (chars)) return false;
-                    }
-                }
-                
-                return true;
-            }
-            
-            
-            WCInclExclFilter (final String [] inclusions,
-                              final String [] exclusions)
-            {
-                if ((inclusions == null) || (inclusions.length == 0))
-                    m_inclusions = null;
-                else
-                {
-                    m_inclusions = new WCMatcher [inclusions.length];
-                    
-                    for (int i = 0; i < inclusions.length; ++ i)
-                    {
-                        m_inclusions [i] = WCMatcher.compile (inclusions [i]);
-                    }
-                }
-                
-                if ((exclusions == null) || (exclusions.length == 0))
-                    m_exclusions = null;
-                else
-                {
-                    m_exclusions = new WCMatcher [exclusions.length];
-                    
-                    for (int i = 0; i < exclusions.length; ++ i)
-                    {
-                        m_exclusions [i] = WCMatcher.compile (exclusions [i]);
-                    }
-                }
-            }
-            
-            WCInclExclFilter (final List /* String */ inclusions,
-                              final List /* String */ exclusions)
-            {
-                if ((inclusions == null) || inclusions.isEmpty ())
-                    m_inclusions = null;
-                else
-                {
-                    m_inclusions = new WCMatcher [inclusions.size ()];
-                    
-                    int ii = 0;
-                    for (Iterator i = inclusions.iterator (); i.hasNext (); ++ ii)
-                    {
-                        final String pattern = (String) i.next ();
-                        
-                        m_inclusions [ii] = WCMatcher.compile (pattern);
-                    }
-                }
-                
-                if ((exclusions == null) || exclusions.isEmpty ())
-                    m_exclusions = null;
-                else
-                {
-                    m_exclusions = new WCMatcher [exclusions.size ()];
-                    
-                    int ii = 0;
-                    for (Iterator i = exclusions.iterator (); i.hasNext (); ++ ii)
-                    {
-                        final String pattern = (String) i.next ();
-                        
-                        m_exclusions [ii] = WCMatcher.compile (pattern);
-                    }
-                }
-            }
-            
-            
-            private final WCMatcher [] m_inclusions, m_exclusions;
-            
-        } // end of nested class
-        
-    } // end of nested class
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/instr/InstrProcessor.java b/core/java12/com/vladium/emma/instr/InstrProcessor.java
deleted file mode 100644
index d8e2f2f..0000000
--- a/core/java12/com/vladium/emma/instr/InstrProcessor.java
+++ /dev/null
@@ -1,319 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: InstrProcessor.java,v 1.1.1.1.2.3 2004/07/17 16:57:14 vlad_r Exp $
- */
-package com.vladium.emma.instr;
-
-import java.io.File;
-
-import com.vladium.util.Files;
-import com.vladium.util.IConstants;
-import com.vladium.util.IPathEnumerator;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.Processor;
-import com.vladium.emma.filter.IInclExclFilter;
-
-// ----------------------------------------------------------------------------
-/*
- * This class was not meant to be public by design. It is made to to work around
- * access bugs in reflective invocations. 
- */
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class InstrProcessor extends Processor
-                              implements IPathEnumerator.IPathHandler
-{
-    // public: ................................................................
-    
-    
-    public static final String PROPERTY_EXCLUDE_SYNTHETIC_METHODS   = "instr.exclude_synthetic_methods";
-    public static final String PROPERTY_EXCLUDE_BRIDGE_METHODS      = "instr.exclude_bridge_methods";
-    public static final String PROPERTY_DO_SUID_COMPENSATION        = "instr.do_suid_compensation";
-    
-    public static final String DEFAULT_EXCLUDE_SYNTHETIC_METHODS    = "true";
-    public static final String DEFAULT_EXCLUDE_BRIDGE_METHODS       = "true";
-    public static final String DEFAULT_DO_SUID_COMPENSATION         = "true";
-    
-    public static InstrProcessor create ()
-    {
-        return new InstrProcessorST ();
-    }
-
-    /**
-     * 
-     * @param path [null is equivalent to an empty array]
-     * @param canonical
-     */
-    public synchronized final void setInstrPath (final String [] path, final boolean canonical)
-    {
-        if ((path == null) || (path.length == 0))
-            m_instrPath = IConstants.EMPTY_FILE_ARRAY;
-        else
-            m_instrPath = Files.pathToFiles (path, canonical);
-            
-        m_canonical = canonical;
-    }
-    
-    public synchronized final void setDependsMode (final boolean enable)
-    {
-        m_dependsMode = enable;
-    } 
-    
-    /**
-     * 
-     * @param specs [null is equivalent to no filtering (everything is included)] 
-     */
-    public synchronized final void setInclExclFilter (final String [] specs)
-    {
-        if (specs == null)
-            m_coverageFilter = null;
-        else
-            m_coverageFilter = IInclExclFilter.Factory.create (specs);
-    }
-    
-    /**
-     * 
-     * @param fileName [null unsets the previous override setting]
-     */
-    public synchronized final void setMetaOutFile (final String fileName)
-    {
-        if (fileName == null)
-            m_mdataOutFile = null;
-        else
-        {
-            final File _file = new File (fileName);
-                
-            if (_file.exists () && ! _file.isFile ())
-                throw new IllegalArgumentException ("not a file: [" + _file.getAbsolutePath () + "]");
-                
-            m_mdataOutFile = _file;
-        }
-    }
-    
-    /**
-     * 
-     * @param merge [null unsets the previous override setting]
-     */
-    public synchronized final void setMetaOutMerge (final Boolean merge)
-    {
-        m_mdataOutMerge = merge;
-    }
-    
-    /**
-     * 
-     * @param dir [null unsets the previous setting]
-     */
-    public synchronized final void setInstrOutDir (final String dir)
-    {
-        if (dir == null)
-            m_outDir = null;
-        else
-        {
-            final File _outDir = new File (dir);
-            if (_outDir.exists () && ! _outDir.isDirectory ())
-                throw new IllegalArgumentException ("not a directory: [" + _outDir.getAbsolutePath () + "]");
-                
-            m_outDir = _outDir;
-        }
-    }
-    
-    /**
-     * 
-     * @param mode [may not be null]
-     */
-    public synchronized final void setOutMode (final OutMode mode)
-    {
-        if (mode == null)
-            throw new IllegalArgumentException ("null input: mode");
-            
-        m_outMode = mode;
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected InstrProcessor ()
-    {
-        m_dependsMode = true;
-    }
-
-
-    protected void validateState ()
-    {
-        super.validateState ();
-        
-        if ((m_instrPath == null) || (m_instrPath.length == 0))
-            throw new IllegalStateException ("instrumentation path not set");
-            
-        // [m_coverageFilter can be null]
-
-        if (m_outMode == null)
-            throw new IllegalStateException ("output mode not set");
-        
-        if (m_outMode != OutMode.OUT_MODE_OVERWRITE)
-        { 
-            if (m_outDir == null)
-                throw new IllegalStateException ("output directory not set");
-                        
-            // for non-overwrite modes output directory must not overlap
-            // with the instr path:
-            
-            // [the logic below does not quite catch all possibilities due to
-            // Class-Path: manifest attributes and dir nesting, but it should
-            // intercept most common mistakes]
-            
-            if ($assert.ENABLED)
-            {
-                $assert.ASSERT (m_outDir != null, "m_outDir = null");
-                $assert.ASSERT (m_instrPath != null, "m_instrPath = null");
-            }
-            
-            final File canonicalOutDir = Files.canonicalizeFile (m_outDir);
-            final File [] canonicalInstrPath;
-            
-            if (m_canonical)
-                canonicalInstrPath = m_instrPath;
-            else
-            {
-                canonicalInstrPath = new File [m_instrPath.length];
-                
-                for (int ip = 0; ip < canonicalInstrPath.length; ++ ip)
-                {
-                    canonicalInstrPath [ip] = Files.canonicalizeFile (m_instrPath [ip]);
-                }
-            }
-            
-            // FR_SF988785: detect if the user attempted to use a parent of m_outDir as one of
-            // the input directories (prevents spurious "already instrumented" errors)
-            
-            final int instrPathLength = canonicalInstrPath.length;
-            for (File dir = canonicalOutDir; dir != null; dir = dir.getParentFile ()) // getParentFile() does no real I/O
-            {
-                for (int ip = 0; ip < instrPathLength; ++ ip)
-                {
-                    if (dir.equals (canonicalInstrPath [ip]))
-                        throw new IllegalStateException ("output directory [" + canonicalOutDir + "] cannot be one of the instrumentation path directories (or a child thereof)");
-                }
-            }
-        }
-        
-        // [m_mdataOutFile can be null]
-        // [m_mdataOutMerge can be null]
-    }
-    
-    protected void reset ()
-    {
-        m_classCopies = m_classInstrs = 0;
-    }  
-    
-    protected final void createDir (final File dir, final boolean mkall)
-        throws EMMARuntimeException
-    {
-        if (mkall)
-        {
-            if (! dir.mkdirs () && ! dir.exists ())
-                throw new EMMARuntimeException (IAppErrorCodes.OUT_MKDIR_FAILURE, new Object [] {dir.getAbsolutePath ()}); 
-        }
-        else
-        {
-            if (! dir.mkdir () && ! dir.exists ())
-                throw new EMMARuntimeException (IAppErrorCodes.OUT_MKDIR_FAILURE, new Object [] {dir.getAbsolutePath ()});
-        } 
-    }
-
-    protected final File getFullOutDir (final File pathDir, final boolean isClass)
-    {
-        if (m_outMode == OutMode.OUT_MODE_OVERWRITE)
-        {
-            return pathDir;
-        }
-        else if (m_outMode == OutMode.OUT_MODE_COPY)
-        {
-            return m_outDir;
-        }
-        else if (m_outMode == OutMode.OUT_MODE_FULLCOPY)
-        {
-            return isClass ? Files.newFile (m_outDir, CLASSES) : Files.newFile (m_outDir, LIB);
-        }
-        else throw new IllegalStateException ("invalid out mode state: " + m_outMode);
-    }
-
-    protected final File getFullOutFile (final File pathDir, final File file, final boolean isClass)
-    {
-        return Files.newFile (getFullOutDir (pathDir, isClass), file.getPath ());
-    } 
-
-
-    // caller-settable state [scoped to this runner instance]:
-    
-    protected File [] m_instrPath; // required to be non-null/non-empty for run()
-    protected boolean m_dependsMode;
-    protected boolean m_canonical;
-    protected IInclExclFilter m_coverageFilter; // can be null for run()
-    protected OutMode m_outMode; // required to be set for run()
-    protected File m_outDir; // required to be non-null for run(), unless output mode is 'overwrite'
-    protected File m_mdataOutFile; // user override; can be null for run()
-    protected Boolean m_mdataOutMerge; // user override; can be null for run()
-    
-    // internal run()-scoped state:
-    
-    protected int m_classCopies, m_classInstrs;
-
-    protected static final String CLASSES   = "classes";
-    protected static final String LIB       = "lib";
-    protected static final boolean IN_CLASSES   = true;
-    protected static final boolean IN_LIB       = ! IN_CLASSES;
-
-    // package: ...............................................................
-    
-// TODO: access level [public to workaround Sun's bugs in access level in reflective invocations]
-    public static final class OutMode
-    {
-        public static final OutMode OUT_MODE_COPY = new OutMode ("copy");
-        public static final OutMode OUT_MODE_FULLCOPY = new OutMode ("fullcopy");
-        public static final OutMode OUT_MODE_OVERWRITE = new OutMode ("overwrite");
-        
-        public String getName ()
-        {
-            return m_name;
-        }
-        
-        public String toString ()
-        {
-            return m_name;
-        }
-        
-        public static OutMode nameToMode (final String name)
-        {
-            if (OUT_MODE_COPY.m_name.equals (name))
-                return OUT_MODE_COPY;
-            else if (OUT_MODE_FULLCOPY.m_name.equals (name))
-                return OUT_MODE_FULLCOPY;
-            else if (OUT_MODE_OVERWRITE.m_name.equals (name))
-                return OUT_MODE_OVERWRITE;
-            
-            return null;
-        }
-        
-        private OutMode (final String name)
-        {
-            m_name = name;
-        }
-        
-        
-        private final String m_name;
-        
-    } // end of nested class
-            
-    // private: ...............................................................
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/instr/InstrProcessorST.java b/core/java12/com/vladium/emma/instr/InstrProcessorST.java
deleted file mode 100644
index a7ee0c8..0000000
--- a/core/java12/com/vladium/emma/instr/InstrProcessorST.java
+++ /dev/null
@@ -1,1054 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: InstrProcessorST.java,v 1.1.1.1.2.3 2004/07/16 23:32:28 vlad_r Exp $
- */
-package com.vladium.emma.instr;
-
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileNotFoundException;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-import java.io.RandomAccessFile;
-import java.util.Date;
-import java.util.jar.Attributes;
-import java.util.jar.JarFile;
-import java.util.jar.JarInputStream;
-import java.util.jar.JarOutputStream;
-import java.util.jar.Manifest;
-import java.util.zip.CRC32;
-import java.util.zip.ZipEntry;
-import java.util.zip.ZipInputStream;
-import java.util.zip.ZipOutputStream;
-
-import com.vladium.jcd.cls.ClassDef;
-import com.vladium.jcd.compiler.ClassWriter;
-import com.vladium.jcd.parser.ClassDefParser;
-import com.vladium.logging.Logger;
-import com.vladium.util.ByteArrayOStream;
-import com.vladium.util.Descriptors;
-import com.vladium.util.Files;
-import com.vladium.util.IPathEnumerator;
-import com.vladium.util.IProperties;
-//import com.vladium.util.Profiler;
-import com.vladium.util.Property;
-import com.vladium.util.asserts.$assert;
-import com.vladium.util.exception.Exceptions;
-//import com.vladium.utils.ObjectSizeProfiler;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMAProperties;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.data.CoverageOptions;
-import com.vladium.emma.data.CoverageOptionsFactory;
-import com.vladium.emma.data.DataFactory;
-import com.vladium.emma.data.IMetaData;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-final class InstrProcessorST extends InstrProcessor
-                             implements IAppErrorCodes
-{
-    // public: ................................................................
-
-    // TODO: performance of 'copy' mode could be improved by pushing dir filtering
-    // all the way to the path enumerator [although dir listing is reasonably fast] 
-        
-    
-    // IPathEnumerator.IPathHandler:
-    
-    
-    public final void handleArchiveStart (final File parentDir, final File archive, final Manifest manifest)
-    {
-        final Logger log = m_log;
-        if (log.atTRACE2 ()) log.trace2 ("handleArchiveStart", "[" + parentDir + "] [" + archive + "]");
-        
-        // TODO: pass manifest into this callback, if any
-        // TODO: detect if manifest corresonds to a previously intrumented archive already ?
-        
-        if (DO_DEPENDS_CHECKING)
-        {
-            final File fullArchiveFile = Files.newFile (parentDir, archive);
-            m_currentArchiveTS = fullArchiveFile.lastModified ();
-            
-            if ($assert.ENABLED) $assert.ASSERT (m_currentArchiveTS > 0, "invalid ts: " + m_currentArchiveTS);
-        }
-        
-        if ((m_outMode == OutMode.OUT_MODE_FULLCOPY) || (m_outMode == OutMode.OUT_MODE_OVERWRITE))
-        {
-            final Manifest outManifest = manifest != null
-                ? new Manifest (manifest) // shallow copy
-                : new Manifest (); 
-            
-            // set some basic main attributes:
-            
-            final Attributes mainAttrs = outManifest.getMainAttributes ();
-            if (manifest == null) mainAttrs.put (Attributes.Name.MANIFEST_VERSION,  "1.0");
-            mainAttrs.put (new Attributes.Name ("Created-By"), IAppConstants.APP_NAME + " v" + IAppConstants.APP_VERSION_WITH_BUILD_ID_AND_TAG);
-                            
-            // note: Manifest makes these 72-char-safe
-            
-            mainAttrs.put (Attributes.Name.IMPLEMENTATION_TITLE,  "instrumented version of [" + archive.getAbsolutePath () + "]");
-            mainAttrs.put (Attributes.Name.SPECIFICATION_TITLE,  "instrumented on " + new Date (m_timeStamp) + " [" + Property.getSystemFingerprint () + "]");
-            
-            // TODO: remove entries related to signing            
-        
-            if (m_outMode == OutMode.OUT_MODE_FULLCOPY)
-            {
-                // create an identically named artive in outdir/lib [the stream is
-                // closed in the archive end event handler]:
-                
-                try
-                {
-                    final OutputStream out = new FileOutputStream (getFullOutFile (parentDir, archive, IN_LIB));
-                    
-                    m_archiveOut = outManifest != null ? new JarOutputStream (out, outManifest) : new JarOutputStream (out);
-                }
-                catch (IOException ioe)
-                {
-                    // TODO: error code
-                    throw new EMMARuntimeException (ioe);
-                }
-            }
-            else if (m_outMode == OutMode.OUT_MODE_OVERWRITE)
-            {
-                // create a temp file in the same dir [moved into the original one
-                // in the archive end event handler]:
-                
-                m_origArchiveFile = Files.newFile (parentDir, archive);
-                
-                // length > 3:
-                final String archiveName = Files.getFileName (archive) + IAppConstants.APP_NAME_LC;
-                final String archiveExt = EMMAProperties.PROPERTY_TEMP_FILE_EXT;
-                
-                try
-                {
-                    m_tempArchiveFile = Files.createTempFile (parentDir, archiveName, archiveExt);
-                    if (log.atTRACE2 ()) log.trace2 ("handleArchiveStart", "created temp archive [" + m_tempArchiveFile.getAbsolutePath () + "]");
-                    
-                    final OutputStream out = new FileOutputStream (m_tempArchiveFile);
-                    
-                    m_archiveOut = outManifest != null ? new JarOutputStream (out, outManifest) : new JarOutputStream (out);
-                }
-                catch (IOException ioe)
-                {
-                    // TODO: error code
-                    throw new EMMARuntimeException (ioe);
-                }
-            }
-        }
-    }
-
-    public final void handleArchiveEntry (final JarInputStream in, final ZipEntry entry)
-    {
-        final Logger log = m_log;
-        if (log.atTRACE2 ()) log.trace2 ("handleArchiveEntry", "[" + entry.getName () + "]");
-        
-        final String name = entry.getName ();
-        final String lcName = name.toLowerCase ();
-
-        final boolean notcopymode = (m_outMode == OutMode.OUT_MODE_FULLCOPY) || (m_outMode == OutMode.OUT_MODE_OVERWRITE);
-        
-        boolean copyEntry = false;
-
-        if (lcName.endsWith (".class"))
-        {
-            final String className = name.substring (0, name.length () - 6).replace ('/', '.');
-            
-            // it is possible that a class with this name has already been processed;
-            // however, we can't skip it here because there is no guarantee that
-            // the runtime classpath will be identical to the instrumentation path
-            
-            // [the metadata will still contain only a single entry for a class with
-            // this name: it is the responsibility of the user to ensure that both
-            // files represent the same class; in the future I might use a more
-            // robust internal strategy that uses something other than a class name
-            // as a metadata key]
-            
-            if ((m_coverageFilter == null) || m_coverageFilter.included (className))
-            {
-                InputStream clsin = null;
-                try
-                {
-                    File outFile = null;
-                    File fullOutFile = null;
-                    
-                    if (DO_DEPENDS_CHECKING)
-                    {
-                        // in 'copy' mode 
-                        
-                        if (m_outMode == OutMode.OUT_MODE_COPY)
-                        {
-                            outFile = new File (className.replace ('.', File.separatorChar).concat (".class"));
-                            fullOutFile = getFullOutFile (null, outFile, IN_CLASSES);
-                            
-                            // if we already processed this class name within this instrumentor
-                            // run, skip duplicates in copy mode: 
-                            
-                            if (m_mdata.hasDescriptor (Descriptors.javaNameToVMName (className)))
-                                return;
-                            
-                            // BUG_SF989071: using outFile here instead resulted in
-                            // a zero result regardless of whether the target existed or not
-                            final long outTimeStamp = fullOutFile.lastModified (); // 0 if 'fullOutFile' does not exist or if an I/O error occurs
-                             
-                            if (outTimeStamp > 0)
-                            {
-                                long inTimeStamp = entry.getTime (); // can return -1
-                                if (inTimeStamp < 0) inTimeStamp = m_currentArchiveTS; // default to the archive file timestamp
-                                
-                                if ($assert.ENABLED) $assert.ASSERT (inTimeStamp > 0);
-                                
-                                if (inTimeStamp <= outTimeStamp)
-                                {
-                                    if (log.atVERBOSE ()) log.verbose ("destination file [" + outFile + "] skipped: more recent than the source");
-                                    return;
-                                }
-                            }
-                        }
-                    }
-                    
-                    readZipEntry (in, entry);
-                    
-                    final ClassDef clsDef = ClassDefParser.parseClass (m_readbuf, m_readpos);
-                    
-                    m_visitor.process (clsDef, m_outMode == OutMode.OUT_MODE_OVERWRITE, true, true, m_instrResult);
-                    if (m_instrResult.m_instrumented)
-                    {
-                        if ($assert.ENABLED) $assert.ASSERT (m_instrResult.m_descriptor != null, "no descriptor created for an instrumented class");
-                        
-                        ++ m_classInstrs;
-                        
-                        // update metadata [if this class has not been seen before]:
-                        
-                        m_mdata.add (m_instrResult.m_descriptor, false);
-                        
-                        // class def modified: write it to an array and submit a write job
-                        
-                        m_baos.reset ();
-                        ClassWriter.writeClassTable (clsDef, m_baos);
-                        
-                        if (notcopymode)
-                        {
-                            // [destination is a zip entry]
-                            
-                            entry.setTime (m_timeStamp);
-                            addJob (new EntryWriteJob (m_archiveOut, m_baos.copyByteArray (), entry, false));
-                        }
-                        else // copy mode
-                        {
-                            // [destination is a file]
-                            
-                            if (! DO_DEPENDS_CHECKING) // this block is just a complement to the one above (where fullOutFile is inited)
-                            {
-                                outFile = new File (className.replace ('.', File.separatorChar).concat (".class"));
-                                fullOutFile = getFullOutFile (null, outFile, IN_CLASSES);
-                            }
-                        
-                            addJob (new FileWriteJob (fullOutFile, m_baos.copyByteArray (), true));
-                        }
-                    }   
-                    else if (notcopymode)
-                    {
-                        // original class def already read into m_readbuf:
-                        // clone the array and submit an entry write job
-                         
-                        final byte [] data = new byte [m_readpos];
-                        System.arraycopy (m_readbuf, 0, data, 0, data.length);
-                        ++ m_classCopies;
-                        
-                        entry.setTime (m_timeStamp);
-                        addJob (new EntryWriteJob (m_archiveOut, data, entry, true));
-                    }
-                }
-                catch (FileNotFoundException fnfe)
-                {
-                    // ignore: this should never happen
-                    if ($assert.ENABLED)
-                    {
-                        fnfe.printStackTrace (System.out);
-                    }
-                }
-                catch (IOException ioe)
-                {
-                    // TODO: error code
-                    throw new EMMARuntimeException (ioe);
-                }
-                finally
-                {
-                    if (clsin != null)
-                        try
-                        {
-                            clsin.close ();
-                        }
-                        catch (Exception e)
-                        {
-                            // TODO: error code
-                            throw new EMMARuntimeException (e);
-                        }
-                }
-            }
-            else
-            {
-                // copy excluded .class entries in full copy and overwrite modes:
-                copyEntry = notcopymode;
-            }
-        }
-        else
-        {
-            // copy non-.class entries in full copy and overwrite modes:
-            copyEntry = notcopymode;
-            
-            // skipping these entries here is important: this is done as a complement
-            // to Sun jar API workarounds as detailed in PathEnumerator.enumeratePathArchive():
-            
-            if (copyEntry && name.equalsIgnoreCase ("META-INF/"))
-                copyEntry = false;
-            if (copyEntry && name.equalsIgnoreCase (JarFile.MANIFEST_NAME))
-                copyEntry = false;
-                
-            // TODO: skip signature-related entries (.SF and .RSA/.DSA/.PGP)
-        }
-        
-        if (copyEntry)
-        {
-            try
-            {
-                readZipEntry (in, entry);
-                
-                final byte [] data = new byte [m_readpos];
-                System.arraycopy (m_readbuf, 0, data, 0, data.length);
-                ++ m_classCopies;
-                
-                entry.setTime (m_timeStamp);
-                addJob (new EntryWriteJob (m_archiveOut, data, entry, true));
-            }
-            catch (IOException ioe)
-            {
-                // TODO: error code
-                throw new EMMARuntimeException (ioe);
-            }
-        }
-    }
-        
-    public final void handleArchiveEnd (final File parentDir, final File archive)
-    {
-        final Logger log = m_log;
-        if (log.atTRACE2 ()) log.trace2 ("handleArchiveEnd", "[" + parentDir + "] [" + archive + "]");
-        
-        m_currentArchiveTS = Long.MAX_VALUE;
-        
-        if ((m_outMode == OutMode.OUT_MODE_FULLCOPY) || (m_outMode == OutMode.OUT_MODE_OVERWRITE))
-        {
-            try
-            {
-                drainJobQueue (); // drain the queue before closing the archive
-                
-                m_archiveOut.flush ();
-                m_archiveOut.close ();
-                m_archiveOut = null;
-            }
-            catch (IOException ioe)
-            {
-                // TODO: error code
-                throw new EMMARuntimeException (ioe);
-            }
-            
-            // in overwrite mode replace the original archive with the temp archive:
-             
-            if (m_outMode == OutMode.OUT_MODE_OVERWRITE)
-            {
-                if (! Files.renameFile (m_tempArchiveFile, m_origArchiveFile, true)) // overwrite the original archive
-                {
-                    // TODO: disable temp file cleanup in this case so that the user
-                    // could do it manually later?
-                    
-                    // error code
-                    throw new EMMARuntimeException ("could not rename temporary file [" + m_tempArchiveFile + "] to [" + m_origArchiveFile + "]: make sure the original file is not locked and can be deleted");
-                }
-                else
-                {
-                    if (log.atTRACE2 ()) log.trace2 ("handleArchiveEnd", "renamed temp archive [" + m_tempArchiveFile.getAbsolutePath () + "] to [" + m_origArchiveFile + "]");
-                    m_origArchiveFile = m_tempArchiveFile = null;
-                }
-            }
-        }
-    }
-
-
-    public final void handleDirStart (final File pathDir, final File dir)
-    {
-        final Logger log = m_log;
-        if (log.atTRACE2 ()) log.trace2 ("handleDirStart", "[" + pathDir + "] [" + dir + "]");
-        
-        // in full copy mode, create all dirs here; in copy mode, do it as part
-        // of writing each individual file:
-        
-        if (m_outMode == OutMode.OUT_MODE_FULLCOPY)
-        {
-            final File saveDir = new File (getFullOutDir (pathDir, IN_CLASSES), dir.getPath ());
-            createDir (saveDir, true);
-        }
-    }
-
-    public final void handleFile (final File pathDir, final File file)
-    {
-        final Logger log = m_log;
-        if (log.atTRACE2 ()) log.trace2 ("handleFile", "[" + pathDir + "] [" + file + "]");
-        
-        final String name = file.getPath ();
-        final String lcName = name.toLowerCase ();
-
-        final boolean fullcopymode = (m_outMode == OutMode.OUT_MODE_FULLCOPY);
-        final boolean mkdir = (m_outMode == OutMode.OUT_MODE_COPY);
-        
-
-        boolean copyFile = false;
-
-        if (lcName.endsWith (".class"))
-        {
-            final String className = name.substring (0, name.length () - 6).replace (File.separatorChar, '.');
-            
-            // it is possible that a class with this name has already been processed;
-            // however, we can't skip it here because there is no guarantee that
-            // the runtime classpath will be identical to the instrumentation path
-            
-            // [the metadata will still contain only a single entry for a class with
-            // this name: it is the responsibility of the user to ensure that both
-            // files represent the same class; in the future I might use a more
-            // robust internal strategy that uses something other than a class name
-            // as a metadata key]
-            
-            if ((m_coverageFilter == null) || m_coverageFilter.included (className))
-            {
-                InputStream clsin = null;
-                try
-                {
-                    final File inFile = Files.newFile (pathDir, file.getPath ());
-                    final File fullOutFile = getFullOutFile (pathDir, file, IN_CLASSES);
-                    
-                    if (DO_DEPENDS_CHECKING)
-                    {
-                        if (m_outMode == OutMode.OUT_MODE_COPY)
-                        {
-                            // if we already processed this class name within this instrumentor
-                            // run, skip duplicates in copy mode: 
-                            
-                            if (m_mdata.hasDescriptor (Descriptors.javaNameToVMName (className)))
-                                return;
-                            
-                            // otherwise, instrument only if the dest file is out of date
-                            // wrt to the source file:
-                            
-                            final long outTimeStamp = fullOutFile.lastModified (); // 0 if 'fullOutFile' does not exist or if an I/O error occurs
-                             
-                            if (outTimeStamp > 0)
-                            {
-                                final long inTimeStamp = inFile.lastModified ();
-                                
-                                if (inTimeStamp <= outTimeStamp)
-                                {
-                                    if (log.atVERBOSE ()) log.verbose ("destination file [" + fullOutFile + "] skipped: more recent that the source file");
-                                    return;
-                                }
-                            }
-                        }
-                    }
-                    
-                    readFile (inFile);
-                    
-                    ClassDef clsDef = ClassDefParser.parseClass (m_readbuf, m_readpos);
-
-                    // in non-overwrite modes, bail if src file already instrumented:
-                    m_visitor.process (clsDef, m_outMode == OutMode.OUT_MODE_OVERWRITE, true, true, m_instrResult);
-                    if (m_instrResult.m_instrumented)
-                    {
-                        if ($assert.ENABLED) $assert.ASSERT (m_instrResult.m_descriptor != null, "no descriptor created for an instrumented class");
-                        
-                        ++ m_classInstrs;
-                        
-                        // update metadata [if this class has not been seen before]:
-       
-//       ObjectSizeProfiler.SizeProfile profile = ObjectSizeProfiler.profile (m_instrResult.m_descriptor, true);
-//       System.out.println (clsDef.getName () + " metadata:");
-//       System.out.println (profile.root ().dump (0.2));
-                        
-                        m_mdata.add (m_instrResult.m_descriptor, false);
-
-                        // class def modified: write it to an array and submit a write job
-                        
-                        m_baos.reset ();
-                        ClassWriter.writeClassTable (clsDef, m_baos);
-                        clsDef = null;
-                                                
-                        final byte [] outdata = m_baos.copyByteArray ();
-                        
-                        addJob (new FileWriteJob (fullOutFile, outdata, mkdir));
-                    }   
-                    else if (fullcopymode)
-                    {
-                        // original class def already read into m_readbuf:
-                        // clone the array and submit a file write job
-                        
-                        clsDef = null;
-                        
-                        final byte [] outdata = new byte [m_readpos];
-                        System.arraycopy (m_readbuf, 0, outdata, 0, m_readpos);
-                        ++ m_classCopies;
-                        
-                        addJob (new FileWriteJob (fullOutFile, outdata, mkdir));
-                    }
-                }
-                catch (FileNotFoundException fnfe)
-                {
-                    // ignore: this should never happen
-                    if ($assert.ENABLED)
-                    {
-                        fnfe.printStackTrace (System.out);
-                    }
-                }
-                catch (IOException ioe)
-                {
-                    // TODO: error code
-                    throw new EMMARuntimeException (ioe);
-                }
-                finally
-                {
-                    if (clsin != null)
-                        try
-                        {
-                            clsin.close ();
-                        }
-                        catch (Exception e)
-                        {
-                            // TODO: error code
-                            throw new EMMARuntimeException (e);
-                        }
-                }
-            }
-            else
-            {
-                // copy excluded .class files in full copy mode:
-                copyFile = fullcopymode;
-            }
-        }
-        else
-        {
-            // copy non-.class files in full copy mode:
-            copyFile = fullcopymode;
-        }
-        
-        if (copyFile)
-        {
-            try
-            {
-                final File inFile = Files.newFile (pathDir, file.getPath ());
-                readFile (inFile);
-                
-                final byte [] data = new byte [m_readpos];
-                System.arraycopy (m_readbuf, 0, data, 0, data.length);
-                ++ m_classCopies;
-                
-                final File outFile = getFullOutFile (pathDir, file, IN_CLASSES);
-    
-                addJob (new FileWriteJob (outFile, data, mkdir));
-            }
-            catch (IOException ioe)
-            {
-                // TODO: error code
-                throw new EMMARuntimeException (ioe);
-            }
-        }
-    }
-
-    public final void handleDirEnd (final File pathDir, final File dir)
-    {
-        final Logger log = m_log;
-        if (log.atTRACE2 ()) log.trace2 ("handleDirEnd", "[" + pathDir + "] [" + dir + "]");
-        
-        // in overwrite mode, flush the job queue before going to the next directory:
-        
-        if (m_outMode == OutMode.OUT_MODE_OVERWRITE)
-        {
-            try
-            {
-                drainJobQueue ();
-            }
-            catch (IOException ioe)
-            {
-                // TODO: error code
-                throw new EMMARuntimeException (ioe);
-            }
-        }
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected void reset ()
-    {
-        m_visitor = null;
-        m_mdata = null;
-        m_readbuf = null;
-        m_baos = null;
- 
-        for (int j = 0; j < m_jobs.length; ++ j) m_jobs [j] = null;
-               
-        if (CLEANUP_TEMP_ARCHIVE_ON_ERRORS)
-        {
-            if (m_archiveOut != null) 
-                try { m_archiveOut.close (); } catch (Exception ignore) {} // unlock the file descriptor for deletion
-            
-            if (m_tempArchiveFile != null)
-                m_tempArchiveFile.delete ();
-        }
-        
-        m_archiveOut = null;
-        m_origArchiveFile = null;
-        m_tempArchiveFile = null;
-        
-        super.reset ();
-    }
-    
-    protected void _run (final IProperties toolProperties)
-    {
-        final Logger log = m_log;
-
-        final boolean verbose = log.atVERBOSE ();
-        if (verbose)
-        {
-            log.verbose (IAppConstants.APP_VERBOSE_BUILD_ID);
-            
-            // [assertion: m_instrPath != null]
-            log.verbose ("instrumentation path:");
-            log.verbose ("{");
-            for (int p = 0; p < m_instrPath.length; ++ p)
-            {
-                final File f = m_instrPath [p];
-                final String nonexistent = f.exists () ? "" : "{nonexistent} ";
-                
-                log.verbose ("  " + nonexistent + f.getAbsolutePath ());
-            }
-            log.verbose ("}");
-            
-            // [assertion: m_outMode != null]
-            log.verbose ("instrumentation output mode: " + m_outMode);
-        }
-        else
-        {
-            log.info ("processing instrumentation path ...");
-        }
-        
-        RuntimeException failure = null;
-        try
-        {
-            long start = System.currentTimeMillis ();
-            m_timeStamp = start;
-            
-            // construct instr path enumerator [throws on illegal input only]:
-            final IPathEnumerator enumerator = IPathEnumerator.Factory.create (m_instrPath, m_canonical, this);
-            
-            // create out dir(s):
-            {
-                if (m_outMode != OutMode.OUT_MODE_OVERWRITE) createDir (m_outDir, true);
-                
-                if ((m_outMode == OutMode.OUT_MODE_FULLCOPY))
-                {
-                    final File classesDir = Files.newFile (m_outDir, CLASSES);
-                    createDir (classesDir, false); // note: not using mkdirs() here
-                    
-                    final File libDir = Files.newFile (m_outDir, LIB);
-                    createDir (libDir, false); // note: not using mkdirs() here
-                }
-            }
-            
-            // get the data out settings [note: this is not conditioned on m_dumpRawData]:
-            File mdataOutFile = m_mdataOutFile;
-            Boolean mdataOutMerge = m_mdataOutMerge;
-            {
-                if (mdataOutFile == null)
-                    mdataOutFile = new File (toolProperties.getProperty (EMMAProperties.PROPERTY_META_DATA_OUT_FILE,
-                                                                         EMMAProperties.DEFAULT_META_DATA_OUT_FILE));
-                
-                if (mdataOutMerge == null)
-                {
-                    final String _dataOutMerge = toolProperties.getProperty (EMMAProperties.PROPERTY_META_DATA_OUT_MERGE,
-                                                                             EMMAProperties.DEFAULT_META_DATA_OUT_MERGE.toString ());
-                    mdataOutMerge = Property.toBoolean (_dataOutMerge) ? Boolean.TRUE : Boolean.FALSE;
-                } 
-            }
-            
-            if (verbose)
-            {
-                log.verbose ("metadata output file: " + mdataOutFile.getAbsolutePath ());
-                log.verbose ("metadata output merge mode: " + mdataOutMerge);
-            }
-                        
-            // TODO: can also register an exit hook to clean up temp files, but this is low value
-            
-            // allocate I/O buffers:
-            m_readbuf = new byte [BUF_SIZE]; // don't reuse this across run() calls to reset it to the original size
-            m_readpos = 0;
-            m_baos = new ByteArrayOStream (BUF_SIZE); // don't reuse this across run() calls to reset it to the original size
-            
-            // reset job queue position: 
-            m_jobPos = 0;
-            
-            m_currentArchiveTS = Long.MAX_VALUE;
-
-            final CoverageOptions options = CoverageOptionsFactory.create (toolProperties);            
-            m_visitor = new InstrVisitor (options); // TODO: reuse this?
-            
-            m_mdata = DataFactory.newMetaData (options);
-            
-            // actual work is driven by the path enumerator:
-            try
-            {
-                enumerator.enumerate ();
-                drainJobQueue ();
-            }
-            catch (IOException ioe)
-            {
-                throw new EMMARuntimeException (INSTR_IO_FAILURE, ioe);
-            }
-                       
-            if (log.atINFO ())
-            {
-                final long end = System.currentTimeMillis ();
-                
-                log.info ("instrumentation path processed in " + (end - start) + " ms");
-                log.info ("[" + m_classInstrs + " class(es) instrumented, " + m_classCopies + " resource(s) copied]");
-            }
-            
-            // persist metadata:
-            try
-            {
-                // TODO: create an empty file earlier to catch any errors sooner? [to avoid scenarios where a user waits throught the entire instr run to find out the file could not be written to]
-                
-                if ($assert.ENABLED) $assert.ASSERT (mdataOutFile != null, "m_metadataOutFile is null");
-                
-                if (verbose)
-                {
-                    if (m_mdata != null)
-                    {
-                        log.verbose ("metadata contains " + m_mdata.size () + " entries");
-                    }
-                }
-                
-                if (m_mdata.isEmpty ())
-                {
-                    log.info ("no output created: metadata is empty");
-                }
-                else
-                {
-                    start = System.currentTimeMillis ();
-                    DataFactory.persist (m_mdata, mdataOutFile, mdataOutMerge.booleanValue ());
-                    final long end = System.currentTimeMillis ();
-                    
-                    if (log.atINFO ())
-                    {
-                        log.info ("metadata " + (mdataOutMerge.booleanValue () ? "merged into" : "written to") + " [" + mdataOutFile.getAbsolutePath () + "] {in " + (end - start) + " ms}");
-                    }
-                }
-            }
-            catch (IOException ioe)
-            {
-                throw new EMMARuntimeException (OUT_IO_FAILURE, new Object [] {mdataOutFile.getAbsolutePath ()}, ioe);
-            }
-        }
-        catch (SecurityException se)
-        {
-            failure = new EMMARuntimeException (SECURITY_RESTRICTION, new String [] {IAppConstants.APP_NAME}, se);
-        }
-        catch (RuntimeException re)
-        {
-            failure = re;
-        }
-        finally
-        {
-            reset ();
-        }
-        
-        if (failure != null)
-        {
-            if (Exceptions.unexpectedFailure (failure, EXPECTED_FAILURES))
-            {
-                throw new EMMARuntimeException (UNEXPECTED_FAILURE,
-                                                new Object [] {failure.toString (), IAppConstants.APP_BUG_REPORT_LINK},
-                                                failure);
-            }
-            else
-                throw failure;
-        }
-    }
-
-    // package: ...............................................................
-    
-    
-    InstrProcessorST ()
-    {
-        m_jobs = new Job [JOB_QUEUE_SIZE];
-        m_instrResult = new InstrVisitor.InstrResult ();
-    }
-    
-    
-    static void writeFile (final byte [] data, final File outFile, final boolean mkdirs)
-        throws IOException
-    {
-        RandomAccessFile raf = null;
-        try
-        {
-            if (mkdirs)
-            {
-                final File parent = outFile.getParentFile ();
-                if (parent != null) parent.mkdirs (); // no error checking here [errors will be throw below]
-            }
-            
-            raf = new RandomAccessFile (outFile, "rw");
-            if (DO_RAF_EXTENSION) raf.setLength (data.length);
-            
-            raf.write (data);
-        } 
-        finally
-        {
-            if (raf != null) raf.close (); // note: intentionally letting the exception percolate up
-        }
-    }
-    
-    static void writeZipEntry (final byte [] data, final ZipOutputStream out, final ZipEntry entry, final boolean isCopy)
-        throws IOException
-    {
-        if (isCopy)
-        {
-            out.putNextEntry (entry); // reusing ' entry' is ok here because we are not changing the data 
-            try
-            {
-                out.write (data);
-            }
-            finally
-            {
-                out.closeEntry ();
-            }
-        }
-        else
-        {
-            // need to compute the checksum which slows things down quite a bit:
-            
-            final ZipEntry entryCopy = new ZipEntry (entry.getName ());
-            entryCopy.setTime (entry.getTime ()); // avoid repeated calls to System.currentTimeMillis() inside the zip stream
-            entryCopy.setMethod (ZipOutputStream.STORED);
-            // [directory status is implicit in the name]
-            entryCopy.setSize (data.length);
-            entryCopy.setCompressedSize (data.length);
-            
-            final CRC32 crc = new CRC32 ();
-            crc.update (data);
-            entryCopy.setCrc (crc.getValue ());
-            
-            out.putNextEntry (entryCopy);
-            try
-            {
-                out.write (data);
-            }
-            finally
-            {
-                out.closeEntry ();
-            }
-        }
-    }
-            
-    // private: ...............................................................
-    
-    
-    private static abstract class Job
-    {
-        protected abstract void run () throws IOException;
-        
-    } // end of nested class
-    
-    
-    private static final class FileWriteJob extends Job
-    {
-        protected void run () throws IOException
-        {
-            writeFile (m_data, m_outFile, m_mkdirs);
-            m_data = null;
-        }
-        
-        FileWriteJob (final File outFile, final byte [] data, final boolean mkdirs)
-        {
-            m_outFile = outFile;
-            m_data = data;
-            m_mkdirs = mkdirs;
-        }
-        
-
-        final File m_outFile;
-        final boolean m_mkdirs;
-        byte [] m_data;
-        
-    } // end of nested class
-    
-
-    private static final class EntryWriteJob extends Job
-    {
-        protected void run () throws IOException
-        {
-            writeZipEntry (m_data, m_out, m_entry, m_isCopy);
-            m_data = null;
-        }
-        
-        EntryWriteJob (final ZipOutputStream out, final byte [] data, final ZipEntry entry, final boolean isCopy)
-        {
-            m_out = out;
-            m_data = data;
-            m_entry = entry;
-            m_isCopy = isCopy;
-        }
-        
-
-        final ZipOutputStream m_out;
-        byte [] m_data;
-        final ZipEntry m_entry;
-        final boolean m_isCopy;
-        
-    } // end of nested class
-
-    
-    private void addJob (final Job job)
-        throws FileNotFoundException, IOException
-    {
-        if (m_jobPos == JOB_QUEUE_SIZE) drainJobQueue ();
-        
-        m_jobs [m_jobPos ++] = job;
-    }
-    
-    private void drainJobQueue ()
-        throws IOException
-    {
-        for (int j = 0; j < m_jobPos; ++ j)
-        {
-            final Job job = m_jobs [j];
-            if (job != null) // a guard just in case
-            {
-                m_jobs [j] = null;
-                job.run ();
-            }
-        }
-        
-        m_jobPos = 0;
-    }
-        
-    /*
-     * Reads into m_readbuf (m_readpos is updated correspondingly)
-     */
-    private void readFile (final File file)
-        throws IOException
-    {
-        final int length = (int) file.length ();
-        
-        ensureReadCapacity (length);
-        
-        InputStream in = null;
-        try
-        {
-            in = new FileInputStream (file);
-            
-            int totalread = 0;
-            for (int read;
-                 (totalread < length) && (read = in.read (m_readbuf, totalread, length - totalread)) >= 0;
-                 totalread += read);
-            m_readpos = totalread;
-        } 
-        finally
-        {
-            if (in != null) try { in.close (); } catch (Exception ignore) {} 
-        }
-    }
-    
-    /*
-     * Reads into m_readbuf (m_readpos is updated correspondingly)
-     */
-    private void readZipEntry (final ZipInputStream in, final ZipEntry entry)
-        throws IOException
-    {
-        final int length = (int) entry.getSize (); // can be -1 if unknown
-        
-        if (length >= 0)
-        {
-            ensureReadCapacity (length);
-            
-            int totalread = 0;
-            for (int read;
-                 (totalread < length) && (read = in.read (m_readbuf, totalread, length - totalread)) >= 0;
-                 totalread += read);
-            m_readpos = totalread;
-        }
-        else
-        {
-            ensureReadCapacity (BUF_SIZE);
-            
-            m_baos.reset ();
-            for (int read; (read = in.read (m_readbuf)) >= 0; m_baos.write (m_readbuf, 0, read));
-            
-            m_readbuf = m_baos.copyByteArray ();
-            m_readpos = m_readbuf.length;
-        }
-    }   
- 
-    private void ensureReadCapacity (final int capacity)
-    {
-        if (m_readbuf.length < capacity)
-        {
-            final int readbuflen = m_readbuf.length;
-            m_readbuf = null;
-            m_readbuf = new byte [Math.max (readbuflen << 1, capacity)];
-        }
-    }
-    
-    
-    // internal run()-scoped state:
-    
-    private final Job [] m_jobs;
-    private final InstrVisitor.InstrResult m_instrResult;
-    
-    private InstrVisitor m_visitor;
-    private IMetaData m_mdata;
-    private byte [] m_readbuf;
-    private int m_readpos;
-    private ByteArrayOStream m_baos; // TODO: code to guard this from becoming too large
-    private int m_jobPos;
-    private long m_currentArchiveTS;
-    private File m_origArchiveFile, m_tempArchiveFile;
-    private JarOutputStream m_archiveOut;
-    private long m_timeStamp;
-    
-    
-    private static final int BUF_SIZE = 32 * 1024;
-    private static final int JOB_QUEUE_SIZE = 128; // a reasonable size chosen empirically after testing a few SCSI/IDE machines
-    private static final boolean CLEANUP_TEMP_ARCHIVE_ON_ERRORS = true;
-    private static final boolean DO_RAF_EXTENSION = true;
-    
-    private static final boolean DO_DEPENDS_CHECKING = true;
-    private static final Class [] EXPECTED_FAILURES; // set in <clinit>
-    
-    static
-    {
-        EXPECTED_FAILURES = new Class []
-        {
-            EMMARuntimeException.class,
-            IllegalArgumentException.class,
-            IllegalStateException.class,
-        };
-    }
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/instr/InstrVisitor.java b/core/java12/com/vladium/emma/instr/InstrVisitor.java
deleted file mode 100644
index cfc64f3..0000000
--- a/core/java12/com/vladium/emma/instr/InstrVisitor.java
+++ /dev/null
@@ -1,2209 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: InstrVisitor.java,v 1.1.1.1.2.4 2004/07/16 23:32:28 vlad_r Exp $
- */
-package com.vladium.emma.instr;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Comparator;
-import java.util.Iterator;
-import java.util.List;
-
-import com.vladium.jcd.cls.*;
-import com.vladium.jcd.cls.attribute.*;
-import com.vladium.jcd.cls.constant.CONSTANT_Class_info;
-import com.vladium.jcd.cls.constant.CONSTANT_Long_info;
-import com.vladium.jcd.cls.constant.CONSTANT_Methodref_info;
-import com.vladium.jcd.cls.constant.CONSTANT_String_info;
-import com.vladium.jcd.compiler.CodeGen;
-import com.vladium.jcd.lib.Types;
-import com.vladium.jcd.opcodes.IOpcodes;
-import com.vladium.logging.Logger;
-import com.vladium.util.ByteArrayOStream;
-import com.vladium.util.IConstants;
-import com.vladium.util.IntIntMap;
-import com.vladium.util.IntObjectMap;
-import com.vladium.util.IntSet;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.data.ClassDescriptor;
-import com.vladium.emma.data.CoverageOptions;
-import com.vladium.emma.data.IMetadataConstants;
-import com.vladium.emma.data.MethodDescriptor;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class InstrVisitor extends AbstractClassDefVisitor
-                         implements IClassDefVisitor, IAttributeVisitor, IOpcodes, IConstants
-{
-    // public: ................................................................
-    
-    // TODO: m_instrument is unused
-
-    public static final class InstrResult
-    {
-        public boolean m_instrumented;
-        public ClassDescriptor m_descriptor;
-        
-    } // end of nested class    
-    
-    public InstrVisitor (final CoverageOptions options)
-    {
-        m_excludeSyntheticMethods = options.excludeSyntheticMethods ();
-        m_excludeBridgeMethods = options.excludeBridgeMethods ();
-        m_doSUIDCompensation = options.doSUIDCompensation ();
-        
-        m_log = Logger.getLogger ();
-    }
-    
-    /**
-     * Analyzes 'cls' and/or instruments it for coverage:
-     * <ul>
-     *  <li> if 'instrument' is true, the class definition is instrumented for
-     *       coverage if that is feasible
-     *  <li> if 'metadata' is true, the class definition is analysed
-     *       to create a {@link ClassDescriptor} for the original class definition 
-     * </ul>
-     * This method returns null if 'metadata' is 'false' *or* if 'cls' is an
-     * interface [the latter precludes coverage of interface static
-     * initializers and may be removed in the future].<P>
-     * 
-     * NOTE: if 'instrument' is 'true', the caller should always assume that 'cls'
-     * has been mutated by this method even if it returned null. The caller should
-     * then revert to the original class definition that was created as a
-     * <code>cls.clone()</code> or by retaining the original definition bytes.
-     * This part of contract is for efficienty and also simplifies the implementation. 
-     */
-    public void process (final ClassDef cls,
-                         final boolean ignoreAlreadyInstrumented,
-                         final boolean instrument, final boolean metadata,
-                         final InstrResult out)
-    {
-        out.m_instrumented = false;
-        out.m_descriptor = null;
-        
-        if (! (instrument || metadata)) return; // nothing to do
-
-        if (cls.isInterface ())
-            return; // skip interfaces [may change in the future]
-        else
-        {
-            reset ();
-            
-            m_cls = cls;
-            
-            // TODO: handle classes that cannot be instrumented due to bytecode/JVM limitations
-            m_instrument = instrument;
-            m_metadata = metadata;
-            m_ignoreAlreadyInstrumented = ignoreAlreadyInstrumented;
-            
-            // TODO: create 'no instrumentation' execution path here
-            
-            visit ((ClassDef) null, null); // potentially changes m_instrument and m_metadata
-            
-            if (m_metadata)
-            {
-                setClassName (cls.getName ());
-                
-                out.m_descriptor = new ClassDescriptor (m_classPackageName, m_className, m_classSignature, m_classSrcFileName, m_classMethodDescriptors);
-            }
-            
-            out.m_instrumented = m_instrument;
-        }
-    }
-    
-
-    // IClassDefVisitor:
-    
-    public Object visit (final ClassDef ignore, final Object ctx)
-    {
-        final ClassDef cls = m_cls;
-        final String clsVMName = cls.getName ();
-        final String clsName = Types.vmNameToJavaName (clsVMName);
-        
-        final boolean trace1 = m_log.atTRACE1 (); 
-        if (trace1) m_log.trace1 ("visit", "class: [" + clsVMName + "]");
-        
-        
-        // skip synthetic classes if enabled:
-        if (SKIP_SYNTHETIC_CLASSES && cls.isSynthetic ())
-        {
-            m_instrument = false;
-            m_metadata = false;
-            
-            if (trace1) m_log.trace1 ("visit", "skipping synthetic class");
-            return ctx;
-        }
-        
-        // TODO: ideally, this check should be done in outer scope somewhere
-        if (! m_warningIssued && clsName.startsWith (IAppConstants.APP_PACKAGE))
-        {
-            m_warningIssued = true;
-            
-            m_log.warning (IAppConstants.APP_NAME + " classes appear to be included on the instrumentation");
-            m_log.warning ("path: this is not a correct way to use " + IAppConstants.APP_NAME);
-        }
-        
-        // field uniqueness check done to detect double instrumentation:
-        {
-            final int [] existing = cls.getFields (COVERAGE_FIELD_NAME);
-            if (existing.length > 0)
-            {
-                m_instrument = false;
-                m_metadata = false;
-                
-                if (m_ignoreAlreadyInstrumented)
-                {
-                    if (trace1) m_log.trace1 ("visit", "skipping instrumented class");
-                    return ctx;
-                }
-                else
-                {
-                    // TODO: use a app coded exception
-                    throw new IllegalStateException ("class [" + clsName + "] appears to be instrumented already");
-                }
-            }
-        }
-        
-        final IConstantCollection constants = cls.getConstants ();
-        
-        SyntheticAttribute_info syntheticMarker = null;
-        
-        // cache the location of "Synthetic" string:
-        {
-            if (MARK_ADDED_ELEMENTS_SYNTHETIC)
-                m_syntheticStringIndex = cls.addCONSTANT_Utf8 (Attribute_info.ATTRIBUTE_SYNTHETIC, true);
-        }
-                
-        // add a Fieldref for the runtime coverage collector field:
-        {
-            // note: this is a bit premature if the class has no methods that need
-            // instrumentation
-            // TODO: the mutated version is easily discardable; however, this case
-            // needs attention at metadata/report generation level
-            
-            final int coverageFieldOffset;
-            final String fieldDescriptor = "[[Z";
-            
-            // note that post-4019 builds can modify this field outside of <clinit> (although
-            // it can only happen as part of initializing a set of classes); however, it is legal
-            // to declare this field final:
-            
-            final int fieldModifiers = IAccessFlags.ACC_PRIVATE | IAccessFlags.ACC_STATIC | IAccessFlags.ACC_FINAL;
-            
-            // add declared field:
-            if (MARK_ADDED_ELEMENTS_SYNTHETIC)
-            {
-                final IAttributeCollection fieldAttributes = ElementFactory.newAttributeCollection (1);
-
-                syntheticMarker = new SyntheticAttribute_info (m_syntheticStringIndex);
-                fieldAttributes.add (syntheticMarker);
-    
-                coverageFieldOffset = cls.addField (COVERAGE_FIELD_NAME, fieldDescriptor,
-                    fieldModifiers, fieldAttributes);
-            }
-            else
-            {
-                coverageFieldOffset = cls.addField (COVERAGE_FIELD_NAME, fieldDescriptor,
-                    fieldModifiers);
-            }
-            
-            //add fieldref:
-            m_coverageFieldrefIndex = cls.addFieldref (coverageFieldOffset);
-        }
-        
-        // add a Methodref for Runtime.r():
-        {
-            // TODO: compute this without loading Runtime Class?
-            final String classJVMName = "com/vladium/emma/rt/RT";
-            final int class_index = cls.addClassref (classJVMName);
-            
-            // NOTE: keep this descriptor in sync with the actual signature
-            final String methodDescriptor = "([[ZLjava/lang/String;J)V";
-            final int nametype_index = cls.addNameType ("r", methodDescriptor);
-            
-            m_registerMethodrefIndex = constants.add (new CONSTANT_Methodref_info (class_index, nametype_index));
-        }
-        
-        // SF FR 971186: split the init logic into a separate method so it could
-        // be called from regular method headers if necessary: 
-        
-        // add a Methodref for pre-<clinit> method:
-        {
-            // NOTE: keep this descriptor in sync with the actual signature
-            final String methodDescriptor = "()[[Z";
-            final int nametype_index = cls.addNameType (PRECLINIT_METHOD_NAME, methodDescriptor);
-            
-            m_preclinitMethodrefIndex = constants.add (new CONSTANT_Methodref_info (cls.getThisClassIndex (), nametype_index));
-        }
-        
-        // add a CONSTANT_String that corresponds to the class name [in JVM format]:
-        {
-            m_classNameConstantIndex = constants.add (new CONSTANT_String_info (cls.getThisClass ().m_name_index));
-        }
-        
-        // visit method collection:         
-        visit (cls.getMethods (), ctx);
-        
-        // if necessary, do SUID compensation [need to be done after method
-        // visits when it is known whether a <clinit> was added]:
-        if (m_doSUIDCompensation)
-        {
-            // compensation not necessary if the original clsdef already defined <clinit>:
-            boolean compensate = ((m_clinitStatus & IMetadataConstants.METHOD_ADDED) != 0);
-            
-            int existingSUIDFieldCount = 0;
-            
-            if (compensate)
-            {
-                // compensation not necessary if the original clsdef already controlled it via 'serialVersionUID':
-                {
-                    final int [] existing = cls.getFields (SUID_FIELD_NAME);
-                    existingSUIDFieldCount = existing.length;
-                    
-                    if (existingSUIDFieldCount > 0)
-                    {
-                        final IFieldCollection fields = cls.getFields ();
-                        
-                        for (int f = 0; f < existingSUIDFieldCount; ++ f)
-                        {
-                            final Field_info field = fields.get (existing [f]);
-                            if ((field.getAccessFlags () & (IAccessFlags.ACC_STATIC | IAccessFlags.ACC_FINAL))
-                                 == (IAccessFlags.ACC_STATIC | IAccessFlags.ACC_FINAL))
-                            {
-                                // TODO: should also check for presence of a non-zero initializer
-                                
-                                compensate = false;
-                                break;
-                            }
-                        }
-                    }
-                }
-                
-                // compensation not necessary if we can determine that this class
-                // does not implement java.io.Serializable/Externalizable:
-                
-                if (compensate && (cls.getThisClassIndex () == 0)) // no superclasses [this tool can't traverse inheritance chains]
-                {
-                    boolean serializable = false;
-                    
-                    final IInterfaceCollection interfaces = cls.getInterfaces ();
-                    for (int i = 0, iLimit = interfaces.size (); i < iLimit; ++ i)
-                    {
-                        final CONSTANT_Class_info ifc = (CONSTANT_Class_info) constants.get (interfaces.get (i));
-                        final String ifcName = ifc.getName (cls); 
-                        if (JAVA_IO_SERIALIZABLE_NAME.equals (ifcName) || JAVA_IO_EXTERNALIZABLE_NAME.equals (ifcName))
-                        {
-                            serializable = true;
-                            break;
-                        }
-                    }
-                    
-                    if (! serializable) compensate = false;
-                }
-            }
-            
-            if (compensate)
-            {
-                if (existingSUIDFieldCount > 0)
-                {
-                    // if we get here, the class declares a 'serialVersionUID' field
-                    // that is not both static and final and/or is not initialized
-                    // statically: warn that SUID compensation may not work
-                    
-                    m_log.warning ("class [" + clsName + "] declares a 'serialVersionUID'");
-                    m_log.warning ("field that is not static and final: this is likely an implementation mistake");
-                    m_log.warning ("and can interfere with " + IAppConstants.APP_NAME + "'s SUID compensation");
-                }
-                
-                final String fieldDescriptor = "J";
-                final int fieldModifiers = IAccessFlags.ACC_PRIVATE | IAccessFlags.ACC_STATIC | IAccessFlags.ACC_FINAL;
-                final IAttributeCollection fieldAttributes = ElementFactory.newAttributeCollection (MARK_ADDED_ELEMENTS_SYNTHETIC ? 2 : 1);
-    
-                final int nameIndex = cls.addCONSTANT_Utf8 (Attribute_info.ATTRIBUTE_CONSTANT_VALUE, true);
-                final int valueIndex = constants.add (new CONSTANT_Long_info (cls.computeSUID (true))); // ignore the added <clinit>
-                
-                final ConstantValueAttribute_info initializer = new ConstantValueAttribute_info (nameIndex, valueIndex);
-                fieldAttributes.add (initializer);
-                    
-                if (MARK_ADDED_ELEMENTS_SYNTHETIC)
-                {
-                    if (syntheticMarker == null) syntheticMarker = new SyntheticAttribute_info (m_syntheticStringIndex);
-                    fieldAttributes.add (syntheticMarker);
-                }
-                
-                cls.addField (SUID_FIELD_NAME, fieldDescriptor, fieldModifiers, fieldAttributes);
-            }
-            
-        } // if (m_doSUIDCompensation)
-        
-        // visit class attributes [to get src file name, etc]:
-        visit (cls.getAttributes (), ctx);
-        
-        return ctx;
-    }
-
-    
-    public Object visit (final IMethodCollection methods, final Object ctx)
-    {
-        final ClassDef cls = m_cls;
-        
-        final boolean trace2 = m_log.atTRACE2 ();
-        
-        final int originalMethodCount = methods.size ();
-        final boolean constructMetadata = m_metadata;
-        
-        // create block count map: TODO: is the extra slot really needed?
-        // - create [potentially unused] slot for added <clinit>
-        m_classBlockCounts = new int [originalMethodCount + 1];        
-        
-        if (constructMetadata)
-        {
-            // prepare to collect metadata:
-            m_classBlockMetadata = new int [originalMethodCount + 1] [] []; // same comments as above
-            
-            m_classMethodDescriptors = new MethodDescriptor [originalMethodCount];
-        }
-        
-       
-        // visit each original method:
-        
-        for (int m = 0; m < originalMethodCount; ++ m)
-        {
-            final Method_info method = methods.get (m);
-            m_methodName = method.getName (cls); 
-            if (trace2) m_log.trace2 ("visit", (method.isSynthetic () ? "synthetic " : "") + "method #" + m + ": [" + m_methodName + "]");
-            
-            final boolean isClinit = IClassDefConstants.CLINIT_NAME.equals (m_methodName);
-                        
-            // TODO: research whether synthetic methods add nontrivially to line coverage or not
-            
-            boolean excluded = false;
-            
-            if (! isClinit)
-            {
-                if (m_excludeSyntheticMethods && method.isSynthetic ())
-                {
-                    excluded = true;
-                    if (trace2) m_log.trace2 ("visit", "skipped synthetic method");
-                }
-                else if (m_excludeBridgeMethods && method.isBridge ())
-                {
-                    excluded = true;
-                    if (trace2) m_log.trace2 ("visit", "skipped bridge method");
-                } 
-            }
-            
-            if (excluded)
-            {
-                if (constructMetadata)
-                {
-                    m_classMethodDescriptors [m] = new MethodDescriptor (m_methodName, method.getDescriptor (cls), IMetadataConstants.METHOD_EXCLUDED, m_methodBlockSizes, null, 0);
-                }
-            }
-            else
-            {
-                if ((method.getAccessFlags () & (IAccessFlags.ACC_ABSTRACT | IAccessFlags.ACC_NATIVE)) != 0)
-                {
-                    if (constructMetadata)
-                    {
-                        m_classMethodDescriptors [m] = new MethodDescriptor (m_methodName, method.getDescriptor (cls), IMetadataConstants.METHOD_ABSTRACT_OR_NATIVE, m_methodBlockSizes, null, 0);
-                    }
-                    
-                    if (trace2) m_log.trace2 ("visit", "skipped " + (method.isAbstract () ? "abstract" : "native") + " method");
-                }
-                else // this is a regular, non-<clinit> method that has bytecode:
-                {
-                    // reset first line:
-                    m_methodFirstLine = 0;
-                    
-                    // set current method ID:
-                    m_methodID = m;
-                    
-                    if (isClinit)
-                    {
-                        // if <clinit> found: note the ID but delay processing until the very end
-                        m_clinitID = m;
-                        if (trace2) m_log.trace2 ("visit", "<clinit> method delayed");
-                    }
-                    else
-                    {
-                        // visit attributes [skip visit (IAttributeCollection) method]:    
-                        final IAttributeCollection attributes = method.getAttributes ();
-                        final int attributeCount = attributes.size ();
-                        for (int a = 0; a < attributeCount; ++ a)
-                        {
-                            final Attribute_info attribute = attributes.get (a);
-                            attribute.accept (this, ctx);
-                        }
-                        
-                        if (constructMetadata)
-                        {
-                            if ($assert.ENABLED) $assert.ASSERT (m_classBlockCounts [m_methodID] > 0, "invalid block count for method " + m_methodID + ": " + m_classBlockCounts [m_methodID]);
-                            if ($assert.ENABLED) $assert.ASSERT (m_methodBlockSizes != null && m_methodBlockSizes.length == m_classBlockCounts [m_methodID], "invalid block sizes map for method " + m_methodID);
-                            
-                            final int [][] methodBlockMetadata = m_classBlockMetadata [m_methodID];
-                            final int status = (methodBlockMetadata == null ? IMetadataConstants.METHOD_NO_LINE_NUMBER_TABLE : 0);
-                            
-                            m_classMethodDescriptors [m] = new MethodDescriptor (m_methodName, method.getDescriptor (cls), status, m_methodBlockSizes, methodBlockMetadata, m_methodFirstLine);
-                        }
-                    }                
-                }
-            }
-        }
-        
-        // add <clinit> (and instrument if needed) [a <clinit> is always needed
-        // even if there are no other instrumented method to act as a load hook]:
-        
-        final boolean instrumentClinit = false; // TODO: make use of this [to limit instrumentation to clinitHeader only], take into account whether we added and whether it is synthetic
-        final Method_info clinit;
-        
-        if (m_clinitID >= 0)
-        {
-            // <clinit> existed in the original class: needs to be covered
-            
-            // m_clinitStatus = 0;
-            clinit = methods.get (m_clinitID);
-            
-            m_classInstrMethodCount = originalMethodCount;
-        }
-        else
-        {
-            // there is no <clinit> defined by the original class: add one [and mark it synthetic]
-            
-            m_clinitStatus = IMetadataConstants.METHOD_ADDED;  // mark as added by us
-            
-            final int attribute_name_index = cls.addCONSTANT_Utf8 (Attribute_info.ATTRIBUTE_CODE, true);
-            final int name_index = cls.addCONSTANT_Utf8 (IClassDefConstants.CLINIT_NAME, true);
-            final int descriptor_index = cls.addCONSTANT_Utf8 ("()V", true);
-            
-            final IAttributeCollection attributes;
-            
-            if (MARK_ADDED_ELEMENTS_SYNTHETIC)
-                attributes = ElementFactory.newAttributeCollection (2);
-            else
-                attributes = ElementFactory.newAttributeCollection (1);
-            
-            final CodeAttribute_info code = new CodeAttribute_info (attribute_name_index,
-                0, 0,
-                new byte [] {(byte) _return},
-                AttributeElementFactory.newExceptionHandlerTable (0),
-                ElementFactory.newAttributeCollection (0));
-                
-            attributes.add (code);
-            
-            if (MARK_ADDED_ELEMENTS_SYNTHETIC)
-            {
-                attributes.add (new SyntheticAttribute_info (m_syntheticStringIndex));
-            }
-            
-            clinit = new Method_info (IAccessFlags.ACC_STATIC | IAccessFlags.ACC_PRIVATE, name_index, descriptor_index, attributes);
-            
-            m_clinitID = cls.addMethod (clinit);
-            
-            if (trace2) m_log.trace2 ("visit", "added synthetic <clinit> method");
-            
-            // TODO: this should exclude <clinit> if it were added by us
-            m_classInstrMethodCount = originalMethodCount + 1;
-        }
-        
-        if ($assert.ENABLED) $assert.ASSERT (m_classInstrMethodCount >= 0,
-            "m_classInstrMethodCount not set");
-        
-
-        // visit <clinit>:
-        {
-            m_methodFirstLine = 0;
-            m_methodID = m_clinitID;
-            
-            if (trace2) m_log.trace2 ("visit", (clinit.isSynthetic () ? "synthetic " : "") + "method #" + m_methodID + ": [<clinit>]");
-            
-            final IAttributeCollection attributes = clinit.getAttributes ();
-            final int attributeCount = attributes.size ();
-            for (int a = 0; a < attributeCount; ++ a)
-            {
-                final Attribute_info attribute = attributes.get (a);
-                attribute.accept (this, ctx);
-            }
-        }
-
-        // add pre-<clinit> method:
-        
-        {
-            final int attribute_name_index = cls.addCONSTANT_Utf8 (Attribute_info.ATTRIBUTE_CODE, true);
-            final int name_index = cls.addCONSTANT_Utf8 (PRECLINIT_METHOD_NAME, false);
-            final int descriptor_index = cls.addCONSTANT_Utf8 ("()[[Z", false);
-            
-            final IAttributeCollection attributes;
-            
-            if (MARK_ADDED_ELEMENTS_SYNTHETIC)
-                attributes = ElementFactory.newAttributeCollection (2);
-            else
-                attributes = ElementFactory.newAttributeCollection (1);
-            
-            final ByteArrayOStream buf = new ByteArrayOStream (PRECLINIT_INIT_CAPACITY);  
-            {
-                final int [] blockCounts = m_classBlockCounts;
-                final int instrMethodCount = m_classInstrMethodCount; // actual number of methods to instrument may be less than the size of the block map 
-
-                if ($assert.ENABLED) $assert.ASSERT (blockCounts != null && blockCounts.length >= instrMethodCount,
-                    "invalid block count map");
-                
-                // new and set COVERAGE_FIELD:
-                
-                // push first dimension:
-                CodeGen.push_int_value (buf, cls, instrMethodCount);
-                
-                // [stack +1]
-                
-                // new boolean [][]:
-                final int type_index = cls.addClassref ("[[Z");
-                buf.write4 (_multianewarray,
-                            type_index >>> 8,    // indexbyte1
-                            type_index,          // indexbyte2
-                            1); // only one dimension created here
-                
-                // [stack +1]
-                
-                // clone array ref:
-                buf.write4 (_dup,
-                
-                // [stack +2]
-                
-                // store in the static field
-                            _putstatic,
-                            m_coverageFieldrefIndex >>> 8,    // indexbyte1
-                            m_coverageFieldrefIndex);          // indexbyte2
-                
-                // [stack +1]
-                
-                for (int m = 0; m < instrMethodCount; ++ m)
-                {
-                    final int blockCount = blockCounts [m]; 
-                    if (blockCount > 0)
-                    {
-                        // clone array ref:
-                        buf.write (_dup);
-                        
-                        // [stack +2]
-                        
-                        // push outer dim index:
-                        CodeGen.push_int_value (buf, cls, m);
-                        
-                        // [stack +3]
-                        
-                        // push dim:
-                        CodeGen.push_int_value (buf, cls, blockCount);
-                        
-                        // [stack +4]
-                        
-                        // newarray boolean []:
-                        buf.write3 (_newarray,
-                                    4, // "T_BOOLEAN"
-                        
-                        // add subarray to the outer array:
-                                    _aastore);
-                        
-                        // [stack +1]
-                    }
-                }
-                
-                // [stack +1]
-                
-                {
-                    // clone array ref
-                    buf.write (_dup);
-                    
-                    // [stack +2]
-                    
-                    CodeGen.push_constant_index (buf, m_classNameConstantIndex);
-                    
-                    // [stack +3]
-
-                    buf.write3 (_ldc2_w,
-                                m_stampIndex >>> 8,    // indexbyte1
-                                m_stampIndex);         // indexbyte2
-                    
-                    // [stack +5]
-                    
-                    buf.write3 (_invokestatic,
-                                m_registerMethodrefIndex >>> 8,    // indexbyte1
-                                m_registerMethodrefIndex);         // indexbyte2
-                    
-                    // [stack +1]
-                }
-                
-                // pop and return extra array ref:
-                buf.write (_areturn);
-                
-                // [stack +0]
-            }
-
-            final CodeAttribute_info code = new CodeAttribute_info (attribute_name_index,
-                5, 0, // adjust constants if the bytecode emitted above changes
-                EMPTY_BYTE_ARRAY,
-                AttributeElementFactory.newExceptionHandlerTable (0),
-                ElementFactory.newAttributeCollection (0));
-            
-            code.setCode (buf.getByteArray (), buf.size ());
-                
-            attributes.add (code);
-            
-            if (MARK_ADDED_ELEMENTS_SYNTHETIC)
-            {
-                attributes.add (new SyntheticAttribute_info (m_syntheticStringIndex));
-            }
-            
-            final Method_info preclinit = new Method_info (IAccessFlags.ACC_STATIC | IAccessFlags.ACC_PRIVATE, name_index, descriptor_index, attributes);
-            cls.addMethod (preclinit);
-            
-            if (trace2) m_log.trace2 ("visit", "added synthetic pre-<clinit> method");
-        }
-
-        
-        if (constructMetadata)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (m_classBlockCounts [m_methodID] > 0, "invalid block count for method " + m_methodID + " (" + IClassDefConstants.CLINIT_NAME + "): " + m_classBlockCounts [m_methodID]);
-            if ($assert.ENABLED) $assert.ASSERT (m_methodBlockSizes != null && m_methodBlockSizes.length == m_classBlockCounts [m_methodID], "invalid block sizes map for method " + m_methodID);
-            
-            final int [][] methodBlockMetadata = m_classBlockMetadata [m_methodID];
-            m_clinitStatus |= (methodBlockMetadata == null ? IMetadataConstants.METHOD_NO_LINE_NUMBER_TABLE : 0);
-            
-            // TODO: this still does not process not added/synthetic case  
-            
-            if ((m_clinitStatus & IMetadataConstants.METHOD_ADDED) == 0)
-                m_classMethodDescriptors [m_methodID] = new MethodDescriptor (IClassDefConstants.CLINIT_NAME, clinit.getDescriptor (cls), m_clinitStatus, m_methodBlockSizes, methodBlockMetadata, m_methodFirstLine);
-        }
-        
-        return ctx;
-    }
-
-
-    public Object visit (final IAttributeCollection attributes, Object ctx)
-    {
-        for (int a = 0, aCount = attributes.size (); a < aCount; ++ a)
-        {
-            // TODO: define a global way to set the mask set of attrs to be visited
-            attributes.get (a).accept (this, ctx);
-        } 
-
-        return ctx;
-    }
-    
-    
-    // IAttributeVisitor:
-
-    public Object visit (final CodeAttribute_info attribute, final Object ctx)
-    {
-        final boolean trace2 = m_log.atTRACE2 ();
-        final boolean trace3 = m_log.atTRACE3 ();
-        
-        final byte [] code = attribute.getCode ();
-        final int codeSize = attribute.getCodeSize ();
-        
-        if (trace2) m_log.trace2 ("visit", "code attribute for method #" + m_methodID + ": size = " + codeSize);
-        
-        final IntSet leaders = new IntSet ();
-        
-        // instructionMap.get(ip) is the number of instructions in code[0-ip)
-        // [this map will include a mapping for code length as well]
-        final IntIntMap /* int(ip)->instr count */ instructionMap = new IntIntMap ();
-        
-        // add first instruction and all exc handler start pcs:
-        leaders.add (0); 
-        
-        final IExceptionHandlerTable exceptions = attribute.getExceptionTable ();
-        final int exceptionCount = exceptions.size ();
-        for (int e = 0; e < exceptionCount; ++ e)
-        {
-            final Exception_info exception = exceptions.get (e);
-            leaders.add (exception.m_handler_pc);
-        }
-        
-        
-        final IntObjectMap branches = new IntObjectMap ();
-        
-        // determine block leaders [an O(code length) loop]:
-        
-        boolean branch = false;
-        boolean wide = false;
-
-        int instructionCount = 0;
-        instructionMap.put (0, 0);
-        
-        for (int ip = 0; ip < codeSize; )
-        {
-            final int opcode = 0xFF & code [ip];
-            int size = 0; // will be set to -<real size> for special cases in the switch below 
-            
-            //if (trace3) m_log.trace3 ("parse", MNEMONICS [opcode]);
-            // "visitor.visit (opcode, wide, ip, null)":
-            
-            { // "opcode visit" logic:
-                
-                int iv, ov;
-                
-                if (branch)
-                {
-                    // previous instruction was a branch: this one is a leader
-                    leaders.add (ip);
-                    branch = false;
-                }
-                
-                switch (opcode)
-                {
-                    case _ifeq:
-                    case _iflt:
-                    case _ifle:
-                    case _ifne:
-                    case _ifgt:
-                    case _ifge:
-                    case _ifnull:
-                    case _ifnonnull:
-                    case _if_icmpeq:
-                    case _if_icmpne:
-                    case _if_icmplt:
-                    case _if_icmpgt:
-                    case _if_icmple:
-                    case _if_icmpge:
-                    case _if_acmpeq:
-                    case _if_acmpne:
-                    {
-                        //ov = getI2 (code, ip + 1);
-                        int scan = ip + 1;
-                        ov = (code [scan] << 8) | (0xFF & code [++ scan]);
-                        
-                        final int target = ip + ov;
-                        leaders.add (target); 
-                        
-                        branches.put (ip, new IFJUMP2 (opcode, target));
-                        branch = true;
-                    }
-                    break;
-
-
-                    case _goto:
-                    case _jsr:
-                    {
-                        //ov = getI2 (code, ip + 1);
-                        int scan = ip + 1;
-                        ov = (code [scan] << 8) | (0xFF & code [++ scan]);
-                        
-                        final int target = ip + ov;
-                        leaders.add (target); 
-                        
-                        branches.put (ip, new JUMP2 (opcode, target));
-                        branch = true;
-                    }
-                    break;
-
-
-                    case _lookupswitch:
-                    {
-                        int scan = ip + 4 - (ip & 3); // eat padding
-                        
-                        ov = (code [scan] << 24) | ((0xFF & code [++ scan]) << 16) | ((0xFF & code [++ scan]) << 8) | (0xFF & code [++ scan]);
-                        leaders.add (ip + ov);
-                        
-                        //final int npairs = getU4 (code, scan);
-                        //scan += 4;
-                        final int npairs = ((0xFF & code [++ scan]) << 24) | ((0xFF & code [++ scan]) << 16) | ((0xFF & code [++ scan]) << 8) | (0xFF & code [++ scan]);
-                        
-                        final int [] keys = new int [npairs];
-                        final int [] targets = new int [npairs + 1];
-                        targets [0] = ip + ov;
-                        
-                        for (int p = 0; p < npairs; ++ p)
-                        {
-                            //iv = getI4 (code, scan);
-                            //scan += 4;
-                            iv = (code [++ scan] << 24) | ((0xFF & code [++ scan]) << 16) | ((0xFF & code [++ scan]) << 8) | (0xFF & code [++ scan]);
-                            keys [p] = iv;
-                            
-                            
-                            //ov = getI4 (code, scan);
-                            //scan += 4;
-                            ov = (code [++ scan] << 24) | ((0xFF & code [++ scan]) << 16) | ((0xFF & code [++ scan]) << 8) | (0xFF & code [++ scan]);
-                            targets [p + 1] = ip + ov;
-                            leaders.add (ip + ov);
-                        }
-                        
-                        branches.put (ip, new LOOKUPSWITCH (keys, targets));
-                        branch = true;
-                        
-                        size = ip - scan - 1; // special case
-                    }
-                    break;
-
-                    
-                    case _tableswitch:
-                    {
-                        int scan = ip + 4 - (ip & 3); // eat padding
-                        
-                        ov = (code [scan] << 24) | ((0xFF & code [++ scan]) << 16) | ((0xFF & code [++ scan]) << 8) | (0xFF & code [++ scan]);
-                        leaders.add (ip + ov);
-                                                
-                        //final int low = getI4 (code, scan + 4);
-                        final int low = (code [++ scan] << 24) | ((0xFF & code [++ scan]) << 16) | ((0xFF & code [++ scan]) << 8) | (0xFF & code [++ scan]);
-                        //final int high = getI4 (code, scan + 8);
-                        //scan += 12;
-                        final int high = (code [++ scan] << 24) | ((0xFF & code [++ scan]) << 16) | ((0xFF & code [++ scan]) << 8) | (0xFF & code [++ scan]);
-                        
-                        final int [] targets = new int [high - low + 2];
-                        targets [0] = ip + ov;
-                        
-                        for (int index = low; index <= high; ++ index)
-                        {
-                            //ov = getI4 (code, scan);
-                            ov = (code [++ scan] << 24) | ((0xFF & code [++ scan]) << 16) | ((0xFF & code [++ scan]) << 8) | (0xFF & code [++ scan]);
-                            targets [index - low + 1] = ip + ov;
-                            leaders.add (ip + ov);
-                            //scan += 4;
-                        }
-
-                        branches.put (ip, new TABLESWITCH (low, high, targets));
-                        branch = true;
-                        
-                        size = ip - scan - 1; // special case
-                    }
-                    break;
-                        
-
-                    case _goto_w:
-                    case _jsr_w:
-                    {
-                        int scan = ip + 1;
-                        //ov = getI4 (code, ip + 1);
-                        ov = (code [scan] << 24) | ((0xFF & code [++ scan]) << 16) | ((0xFF & code [++ scan]) << 8) | (0xFF & code [++ scan]);
-                        final int target = ip + ov;
-                        
-                        leaders.add (target);
-                        
-                        branches.put (ip, new JUMP4 (opcode, target));
-                        branch = true;
-                    }
-                    break;
-
-
-                    case _ret:
-                    {
-                        int scan = ip + 1;
-                        iv = wide ? (((0xFF & code [scan]) << 8) | (0xFF & code [++ scan])) : (0xFF & code [scan]);
-                        
-                        branches.put (ip, new RET (opcode, iv));
-                        branch = true;
-                    } 
-                    break; 
-
-
-                    case _athrow:
-                    case _ireturn:
-                    case _lreturn:
-                    case _freturn:
-                    case _dreturn:
-                    case _areturn:
-                    case _return:
-                    {
-                        branches.put (ip, new TERMINATE (opcode));
-                        branch = true;
-                    }
-                    break;
-                    
-                } // end of switch
-                
-            } // end of processing the current opcode
-            
-            
-            // shift to the next instruction [this is the only block that adjusts 'ip']:
-            
-            if (size == 0)
-                size = (wide ? WIDE_SIZE : NARROW_SIZE) [opcode];
-            else
-                size = -size;
-            
-            ip += size;
-            wide = (opcode == _wide);
-            
-            instructionMap.put (ip, ++ instructionCount);
-            
-        } // end of for
-        
-        
-        // split 'code' into an ordered list of basic blocks [O(block count) loops]:
-        
-        final int blockCount = leaders.size ();
-        if (trace2) m_log.trace2 ("visit", "method contains " + blockCount + " basic blocks");
-        
-        final BlockList blocks = new BlockList (blockCount);
-        
-        final int [] _leaders = new int [blockCount + 1]; // room for end-of-code leader at the end 
-        leaders.values (_leaders, 0);
-        _leaders [blockCount] = codeSize;
-        
-        Arrays.sort (_leaders);
-        
-        final int [] _branch_locations = branches.keys (); 
-        Arrays.sort (_branch_locations);
-        
-        final IntIntMap leaderToBlockID = new IntIntMap (_leaders.length);
-        
-        if (m_metadata)
-        {
-            // help construct a MethodDescriptor for the current method:
-            
-            m_methodBlockSizes = new int [blockCount];
-            m_methodBlockOffsets = _leaders;
-        }
-
-        // compute signature even if metadata is not needed (because the instrumented
-        // classdef uses it):
-        consumeSignatureData (m_methodID, _leaders);
-        
-        // pass 1:
-        
-        final int [] intHolder = new int [1];
-        int instr_count = 0, prev_instr_count;
-        
-        for (int bl = 0, br = 0; bl < blockCount; ++ bl)
-        {
-            final Block block = new Block ();
-            blocks.m_blocks.add (block);
-            
-            final int leader = _leaders [bl];
-            
-            block.m_first = leader; // m_first set
-            leaderToBlockID.put (leader, bl);
-            
-            final int next_leader = _leaders [bl + 1];
-            boolean branchDelimited = false;
-            
-            prev_instr_count = instr_count;
-
-            if (_branch_locations.length > br)
-            {
-                final int next_branch_location = _branch_locations [br];
-                if (next_branch_location < next_leader)
-                {
-                    branchDelimited = true;
-                    
-                    block.m_length = next_branch_location - leader; // m_length set
-                    
-                    if ($assert.ENABLED)
-                        $assert.ASSERT (instructionMap.get (next_branch_location, intHolder), "no mapping for " + next_branch_location);
-                    else
-                        instructionMap.get (next_branch_location, intHolder);
-                        
-                    instr_count = intHolder [0] + 1; // [+ 1 for the branch]
-                     
-                    block.m_branch = (Branch) branches.get (next_branch_location);
-                    block.m_branch.m_parentBlockID = bl; // m_branch set
-                    
-                    ++ br;
-                }
-            }
-            
-            if (! branchDelimited)
-            {
-                block.m_length = next_leader - leader; // m_length set
-                
-                if ($assert.ENABLED)
-                    $assert.ASSERT (instructionMap.get (next_leader, intHolder), "no mapping for " + next_leader);
-                else
-                    instructionMap.get (next_leader, intHolder);
-                
-                instr_count = intHolder [0];
-            }
-            
-            block.m_instrCount = instr_count - prev_instr_count; // m_instrCount set
-            
-            if ($assert.ENABLED) $assert.ASSERT (block.m_length == 0 || block.m_instrCount > 0, "invalid instr count for block " + bl + ": " + block.m_instrCount);
-            if (m_metadata) m_methodBlockSizes [bl] = block.m_instrCount; 
-        }
-        
-        // pass 2:
-        
-        final Block [] _blocks = (Block []) blocks.m_blocks.toArray (new Block [blockCount]);
-        
-        for (int l = 0; l < blockCount; ++ l)
-        {
-            final Block block = _blocks [l];
-             
-            if (block.m_branch != null)
-            {
-                final int [] targets = block.m_branch.m_targets;
-                if (targets != null)
-                {
-                    for (int t = 0, targetCount = targets.length; t < targetCount; ++ t)
-                    {
-                        // TODO: HACK ! convert block absolute offsets to block IDs:
-                        
-                        if ($assert.ENABLED)
-                            $assert.ASSERT (leaderToBlockID.get (targets [t], intHolder), "no mapping for " + targets [t]);
-                        else
-                            leaderToBlockID.get (targets [t], intHolder);
-                            
-                        targets [t] = intHolder [0];
-                    }
-                }
-            }
-        }
-
-        
-        // update block count map [used later by <clinit> visit]:
-        m_classBlockCounts [m_methodID] = blockCount;
-        
-        // actual basic block instrumentation:
-        {
-            if (trace2) m_log.trace2 ("visit", "instrumenting... ");
-            
-            // determine the local var index for the var that will alias COVERAGE_FIELD:
-            final int localVarIndex = attribute.m_max_locals ++;
-            
-            if (m_methodID == m_clinitID) // note: m_clinitID can be -1 if <clinit> has not been visited yet
-            {
-                 // add a long stamp constant after all the original methods have been visited:
-             
-                m_stampIndex = m_cls.getConstants ().add (new CONSTANT_Long_info (m_classSignature));
-                
-                blocks.m_header = new clinitHeader (this, localVarIndex);
-            }
-            else
-                blocks.m_header = new methodHeader (this, localVarIndex);
-            
-            int headerMaxStack = blocks.m_header.maxstack ();
-            int methodMaxStack = 0;
-            
-            for (int l = 0; l < blockCount; ++ l)
-            {
-                final Block block = _blocks [l];
-                
-                final CodeSegment insertion = new BlockSegment (this, localVarIndex, l);
-                block.m_insertion = insertion;
-                
-                final int insertionMaxStack = insertion.maxstack (); 
-                if (insertionMaxStack > methodMaxStack)
-                    methodMaxStack = insertionMaxStack;
-            }
-            
-            // update maxstack as needed [it can only grow]:
-            {
-                final int oldMaxStack = attribute.m_max_stack;
-                
-                attribute.m_max_stack += methodMaxStack; // this is not precise, but still need to add because the insertion may be happening at the old maxstack point
-                
-                if (headerMaxStack > attribute.m_max_stack)
-                attribute.m_max_stack = headerMaxStack;
-                
-                if (trace3) m_log.trace3 ("visit", "increasing maxstack by " + (attribute.m_max_stack - oldMaxStack));
-            }
-            
-            if ($assert.ENABLED) $assert.ASSERT (blocks.m_header != null, "header not set");
-        }
-        
-
-        // assemble all blocks into an instrumented code block:
-        if (trace2) m_log.trace2 ("visit", "assembling... ");
-        
-        int newcodeCapacity = codeSize << 1;
-        if (newcodeCapacity < EMIT_CTX_MIN_INIT_CAPACITY) newcodeCapacity = EMIT_CTX_MIN_INIT_CAPACITY;
-
-        final ByteArrayOStream newcode = new ByteArrayOStream (newcodeCapacity); // TODO: empirical capacity
-        final EmitCtx emitctx = new EmitCtx (blocks, newcode);
-        
-        // create a jump adjustment map:
-        final int [] jumpAdjOffsets = new int [blockCount]; // room for initial 0  + (blockCount - 1)
-        final int [] jumpAdjMap = new int [jumpAdjOffsets.length]; // room for initial 0  + (blockCount - 1)
-        
-        if ($assert.ENABLED) $assert.ASSERT (jumpAdjOffsets.length == jumpAdjMap.length,
-            "jumpAdjOffsets and jumpAdjMap length mismatch");
-        
-        // header:
-        blocks.m_header.emit (emitctx);
-        // jumpAdjOffsets [0] = 0: redundant
-        jumpAdjMap [0] = emitctx.m_out.size ();
-        
-        // rest of blocks:
-        for (int l = 0; l < blockCount; ++ l)
-        {
-            final Block block = _blocks [l];
-            
-            if (l + 1 < blockCount)
-            {
-                jumpAdjOffsets [l + 1] = _blocks [l].m_first + _blocks [l].m_length; // implies the insertion goes just before the branch
-            }
-            
-            block.emit (emitctx, code);
-            
-            // TODO: this breaks if code can shrink:
-            if (l + 1 < blockCount)
-            {
-                jumpAdjMap [l + 1] = emitctx.m_out.size () - _blocks [l + 1].m_first;
-            }
-        }
-        
-        m_methodJumpAdjOffsets = jumpAdjOffsets;
-        m_methodJumpAdjValues = jumpAdjMap;
-        
-        if (trace3)
-        {
-            final StringBuffer s = new StringBuffer ("jump adjustment map:" + EOL);
-            for (int a = 0; a < jumpAdjOffsets.length; ++ a)
-            {
-                s.append ("    " + jumpAdjOffsets [a] + ": +" + jumpAdjMap [a]);
-                if (a < jumpAdjOffsets.length - 1) s.append (EOL);
-            }
-            
-            m_log.trace3 ("visit", s.toString ());
-        }
-        
-        final byte [] _newcode = newcode.getByteArray (); // note: not cloned 
-        final int _newcodeSize = newcode.size ();
-         
-        // [all blocks have had their m_first adjusted]
-        
-        // backpatching pass:        
-        if (trace3) m_log.trace3 ("visit", "backpatching " + emitctx.m_backpatchQueue.size () + " ip(s)");
-        
-        for (Iterator i = emitctx.m_backpatchQueue.iterator (); i.hasNext (); )
-        {
-            final int [] patchData = (int []) i.next ();
-            int ip = patchData [1];
-            
-            if ($assert.ENABLED) $assert.ASSERT (patchData != null, "null patch data for ip " + ip);
-            
-            final int jump = _blocks [patchData [3]].m_first - patchData [2];
-            if ($assert.ENABLED) $assert.ASSERT (jump > 0, "negative backpatch jump offset " + jump + " for ip " + ip);
-            
-            switch (patchData [0])
-            {
-                case 4:
-                {
-                    _newcode [ip ++] = (byte) (jump >>> 24);
-                    _newcode [ip ++] = (byte) (jump >>> 16);
-                    
-                } // *FALL THROUGH*
-                
-                case 2:
-                {
-                    _newcode [ip ++] = (byte) (jump >>> 8);
-                    _newcode [ip] = (byte) jump;
-                }
-            }
-        }
-        
-        attribute.setCode (_newcode, _newcodeSize);
-        if (trace2) m_log.trace2 ("visit", "method assembled into " + _newcodeSize + " code bytes");
-
-        
-        // adjust bytecode offsets in the exception table:
-        final IExceptionHandlerTable exceptionTable = attribute.getExceptionTable ();
-        for (int e = 0; e < exceptionTable.size (); ++ e)
-        {
-            final Exception_info exception = exceptionTable.get (e);
-            
-            int adjSegment = lowbound (jumpAdjOffsets, exception.m_start_pc);
-            exception.m_start_pc += jumpAdjMap [adjSegment];
-            
-            adjSegment = lowbound (jumpAdjOffsets, exception.m_end_pc);
-            exception.m_end_pc += jumpAdjMap [adjSegment];
-            
-            adjSegment = lowbound (jumpAdjOffsets, exception.m_handler_pc);
-            exception.m_handler_pc += jumpAdjMap [adjSegment];
-        }
-
-        
-        // visit other nested attributes [LineNumberAttribute, etc]:    
-        final IAttributeCollection attributes = attribute.getAttributes ();
-        final int attributeCount = attributes.size ();
-        for (int a = 0; a < attributeCount; ++ a)
-        {
-            final Attribute_info nested = attributes.get (a);
-            nested.accept (this, ctx);
-        }
-        
-        return ctx;
-    }
-    
-
-    public Object visit (final LineNumberTableAttribute_info attribute, final Object ctx)
-    {
-        final boolean trace2 = m_log.atTRACE2 ();
-        final boolean trace3 = m_log.atTRACE3 (); 
-        if (trace2) m_log.trace2 ("visit", "attribute: [" + attribute.getName (m_cls) + "]");
-        
-        final int lineCount = attribute.size ();
-        
-        if (m_metadata)
-        {
-            if (trace2) m_log.trace2 ("visit", "processing line number table for metadata...");
-            
-            final int blockCount = m_classBlockCounts [m_methodID];
-            if ($assert.ENABLED) $assert.ASSERT (blockCount > 0, "invalid method block count for method " + m_methodID);
-            
-            final int [][] blockLineMap = new int [blockCount][];
-            
-            if ($assert.ENABLED) $assert.ASSERT (blockCount + 1 == m_methodBlockOffsets.length,
-                    "invalid m_methodBlockOffsets");
-            
-            if (lineCount == 0)
-            {
-                for (int bl = 0; bl < blockCount; ++ bl)
-                    blockLineMap [bl] = EMPTY_INT_ARRAY;
-            }
-            else
-            {
-                // TODO: this code does not work if there are multiple LineNumberTableAttribute attributes for the method
-
-                final LineNumber_info [] sortedLines = new LineNumber_info [attribute.size ()];
-                
-                for (int l = 0; l < lineCount; ++ l)
-                {
-                    final LineNumber_info line = attribute.get (l);
-                    sortedLines [l] = line;
-                }
-                
-                Arrays.sort (sortedLines, LINE_NUMBER_COMPARATOR);
-                
-                // construct block->line mapping: TODO: is the loop below the fastest it can be done?
-                
-                final int [] methodBlockOffsets = m_methodBlockOffsets;
-                
-                LineNumber_info line = sortedLines [0]; // never null
-                LineNumber_info prev_line = null;
-                
-                // remember the first line:
-                m_methodFirstLine = line.m_line_number;
-                
-                for (int bl = 0, l = 0; bl < blockCount; ++ bl)
-                {                   
-                    final IntSet blockLines = new IntSet ();
-                    
-                    if ((prev_line != null) && (line.m_start_pc > methodBlockOffsets [bl]))
-                    {
-                        blockLines.add (prev_line.m_line_number);
-                    }
-                    
-                    while (line.m_start_pc < methodBlockOffsets [bl + 1])
-                    {
-                        blockLines.add (line.m_line_number);
-                        
-                        if (l == lineCount - 1)
-                            break;
-                        else
-                        {
-                            prev_line = line;
-                            line = sortedLines [++ l]; // advance to the next line
-                        }
-                    }
-                    
-                    blockLineMap [bl] = blockLines.values ();
-                }                
-            }
-            
-            m_classBlockMetadata [m_methodID] = blockLineMap;
-            
-            if (trace3)
-            {
-                StringBuffer s = new StringBuffer ("block-line map for method #" + m_methodID + ":");
-                for (int bl = 0; bl < blockCount; ++ bl)
-                {
-                    s.append (EOL);
-                    s.append ("    block " + bl + ": ");
-                    
-                    final int [] lines = blockLineMap [bl];
-                    for (int l = 0; l < lines.length; ++ l)
-                    {
-                        if (l != 0) s.append (", ");
-                        s.append (lines [l]);
-                    }
-                }
-                
-                m_log.trace3 ("visit", s.toString ());
-            }
-        }
-        
-        for (int l = 0; l < lineCount; ++ l)
-        {
-            final LineNumber_info line = attribute.get (l);
-            
-            // TODO: make this faster using either table assist or the sorted array in 'sortedLines'
-            
-            // adjust bytecode offset for line number mapping:
-            int adjSegment = lowbound (m_methodJumpAdjOffsets, line.m_start_pc);                
-            line.m_start_pc += m_methodJumpAdjValues [adjSegment];
-        }
-        
-        return ctx;
-    }
-    
-    // TODO: line var table as well
-    
-
-    // no-op visits:
-
-    public Object visit (final ExceptionsAttribute_info attribute, final Object ctx)
-    {
-        return ctx;
-    }
-    
-    public Object visit (final ConstantValueAttribute_info attribute, final Object ctx)
-    {
-        return ctx;
-    }
-    
-    public Object visit (final SourceFileAttribute_info attribute, final Object ctx)
-    {
-        m_classSrcFileName = attribute.getSourceFile (m_cls).m_value;
-
-        return ctx;
-    }
-
-    public Object visit (final SyntheticAttribute_info attribute, final Object ctx)
-    {
-        return ctx;
-    }
-    
-    public Object visit (final BridgeAttribute_info attribute, final Object ctx)
-    {
-        return ctx;
-    }
-    
-    public Object visit (final InnerClassesAttribute_info attribute, final Object ctx)
-    {
-        return ctx;
-    }
-    
-    public Object visit (final GenericAttribute_info attribute, final Object ctx)
-    {
-        return ctx;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final class BlockList
-    {
-        BlockList ()
-        {
-            m_blocks = new ArrayList ();
-        }
-        
-        BlockList (final int capacity)
-        {
-            m_blocks = new ArrayList (capacity);
-        }
-        
-        final List /* Block */ m_blocks; // TODO: might as well use an array here?
-        CodeSegment m_header;
-        
-    } // end of nested class 
-    
-    
-    private static final class Block
-    {
-        int m_first;    // inclusive offset of the leader instruction [first instr in the block]
-        //int m_last;     // exclusive offset of the last non-branch instruction [excludes possible control transfer at the end]
-        int m_length;   // excluding the branch statement [can be 0]
-        int m_instrCount; // size in instructions, including the [optional] original branch; [m_insertion is not counted] 
-        
-        // NOTE: it is possible that m_first == m_last [the block is empty except for a possible control transfer instr]
-        
-//        public int maxlength ()
-//        {
-//            // TODO: cache
-//            return m_length
-////                + (m_insertion != null ? m_insertion.maxlength () : 0)
-//                + (m_branch != null ? m_branch.maxlength () : 0);
-//        }
-        
-        /**
-         * When this is called, all previous blocks have been written out and 
-         * their m_first have been updated.
-         */
-        void emit (final EmitCtx ctx, final byte [] code) // TODO: move 'code' into 'ctx'
-        {
-            final ByteArrayOStream out = ctx.m_out;
-            final int first = m_first;
-            
-            m_first = out.size (); // update position to be within new code array
-            
-            for (int i = 0, length = m_length; i < length; ++ i)
-            {
-                out.write (code [first + i]);
-            }
-            
-            if (m_insertion != null)
-                m_insertion.emit (ctx);
-            
-            if (m_branch != null)
-                m_branch.emit (ctx);
-        }
-        
-        public CodeSegment m_insertion;
-        public Branch m_branch; // falling through is implied by this being null
-        
-    } // end of nested class
-    
-    
-    static final class EmitCtx
-    {
-        // TODO: profile to check that ByteArrayOStream.write() is not the bottleneck
-        
-        EmitCtx (final BlockList blocks, final ByteArrayOStream out)
-        {
-            m_blocks = blocks;
-            m_out = out;
-            
-            m_backpatchQueue = new ArrayList ();
-        }
-        
-        final BlockList m_blocks;
-        final ByteArrayOStream m_out;
-        final List /* int[4] */ m_backpatchQueue;
-        
-    } // end of nested class
-    
-    
-    /**
-     * A Branch does not add any maxlocals/maxstack requirements.
-     */
-    static abstract class Branch
-    {
-        protected Branch (final int opcode, final int [] targets)
-        {
-            m_opcode = (byte) opcode;
-            m_targets = targets;
-        }
-        
-        /*
-         * Called when targets are block IDs, before emitting. 
-         */
-        int maxlength () { return 1; }
-        
-        abstract void emit (EmitCtx ctx);
-        
-        // TODO: this method must signal when it is necessary to switch to long jump form
-        protected final void emitJumpOffset2 (final EmitCtx ctx, final int ip, final int targetBlockID)
-        {
-            final ByteArrayOStream out = ctx.m_out;
-            
-            if (targetBlockID <= m_parentBlockID)
-            {
-                // backwards branch:
-                final int jumpOffset = ((Block) ctx.m_blocks.m_blocks.get (targetBlockID)).m_first - ip;
-                
-                out.write2 (jumpOffset >>> 8,   // targetbyte1
-                            jumpOffset);         // targetbyte2
-            }
-            else
-            {
-                final int jumpOffsetLocation = out.size (); 
-                
-                // else write out zeros and submit for backpatching:
-                out.write2 (0,
-                            0);
-                
-                ctx.m_backpatchQueue.add (new int [] {2, jumpOffsetLocation, ip, targetBlockID});
-            }
-        }
-        
-        protected final void emitJumpOffset4 (final EmitCtx ctx, final int ip, final int targetBlockID)
-        {
-            final ByteArrayOStream out = ctx.m_out;
-            
-            if (targetBlockID <= m_parentBlockID)
-            {
-                // backwards branch:
-                final int jumpOffset = ((Block) ctx.m_blocks.m_blocks.get (targetBlockID)).m_first - ip;
-                
-                out.write4 (jumpOffset >>> 24,    // targetbyte1
-                            jumpOffset >>> 16,    // targetbyte2
-                            jumpOffset >>> 8,     // targetbyte3
-                            jumpOffset);           // targetbyte4
-            }
-            else
-            {
-                final int jumpOffsetLocation = out.size (); 
-                
-                // else write out zeros and submit for backpatching:
-                out.write4 (0,
-                            0,
-                            0,
-                            0);
-                
-                ctx.m_backpatchQueue.add (new int [] {4, jumpOffsetLocation, ip, targetBlockID});
-            }
-        } 
-        
-        final byte m_opcode;
-        final int [] m_targets; // could be code offsets or block IDs
-        
-        int m_parentBlockID;
-        
-    } // end of nested class    
-    
-    
-    // TODO: these could be static instance-pooled
-    static final class TERMINATE extends Branch // _[x]return, _athrow
-    {
-        TERMINATE (final int opcode)
-        {
-            super (opcode, null);
-        }      
-        
-        int length () { return 1; }
-        
-        void emit (final EmitCtx ctx)
-        {
-            ctx.m_out.write (m_opcode);
-        }
-        
-    } // end of nested class
-    
-    
-    static final class RET extends Branch // [wide] ret
-    {
-        RET (final int opcode, final int varindex)
-        {
-            super (opcode, null);
-            m_varindex = varindex;
-        }      
-        
-        int length () { return (m_varindex <= 0xFF) ? 2 : 3; }
-        
-        void emit (final EmitCtx ctx)
-        {
-            final ByteArrayOStream out = ctx.m_out;
-            
-            if (m_varindex <= 0xFF)
-            {
-                out.write2 (m_opcode,
-                            m_varindex);  // indexbyte
-            }
-            else
-            {
-                out.write4 (_wide,
-                            m_opcode,
-                            m_varindex >>> 8,   // indexbyte1
-                            m_varindex);         // indexbyte2
-            }
-        }
-        
-        final int m_varindex;
-        
-    } // end of nested class
-    
-    
-    static final class JUMP2 extends Branch // _goto, _jsr
-    {
-        JUMP2 (final int opcode, final int target)
-        {
-            super (opcode, new int [] {target});
-        }
-        
-        int maxlength () { return 5; }
-        
-        void emit (final EmitCtx ctx)
-        {
-            final ByteArrayOStream out = ctx.m_out;
-            final int targetBlockID = m_targets [0];
-            final int ip = out.size ();
-            
-            // TODO: switch to 4-byte long form if jump > 32k
-            
-            out.write (m_opcode);
-            emitJumpOffset2 (ctx, ip, targetBlockID);
-        }
-        
-    } // end of nested class
-    
-    
-    static final class JUMP4 extends Branch // _goto_w, _jsr_w
-    {
-        JUMP4 (final int opcode, final int target)
-        {
-            super (opcode, new int [] {target});
-        }
-        
-        int maxlength () { return 5; }
-        
-        void emit (final EmitCtx ctx)
-        {
-            final ByteArrayOStream out = ctx.m_out;
-            final int targetBlockID = m_targets [0];
-            final int ip = out.size ();
-            
-            out.write (m_opcode);
-            emitJumpOffset4 (ctx, ip, targetBlockID);
-        }
-        
-    } // end of nested class
-    
-    
-    static final class IFJUMP2 extends Branch // _ifxxx
-    {
-        IFJUMP2 (final int opcode, final int target)
-        {
-            super (opcode, new int [] {target});
-        }
-        
-        int maxlength () { return 8; }
-        
-        void emit (final EmitCtx ctx)
-        {
-            final ByteArrayOStream out = ctx.m_out;
-            final int targetBlockID = m_targets [0];
-            final int ip = out.size ();
-            
-            // TODO: switch to 8-byte long form if jump > 32k
-            
-            out.write (m_opcode);
-            emitJumpOffset2 (ctx, ip, targetBlockID);
-        }
-        
-    } // end of nested class
-
-    
-    static final class LOOKUPSWITCH extends Branch
-    {
-        LOOKUPSWITCH (final int [] keys, final int [] targets /* first one is default */)
-        {
-            super (_lookupswitch, targets);
-            m_keys = keys;
-        }
-        
-        int maxlength () { return 12 + (m_keys.length << 3); }
-        
-        void emit (final EmitCtx ctx)
-        {
-            final ByteArrayOStream out = ctx.m_out;
-            final int ip = out.size ();
-            
-            out.write (m_opcode);
-            
-            // padding bytes:
-            for (int p = 0, padCount = 3 - (ip & 3); p < padCount; ++ p) out.write (0);
-             
-            // default:
-            emitJumpOffset4 (ctx, ip, m_targets [0]);
-            
-            // npairs count:
-            final int npairs = m_keys.length;
-            out.write4 (npairs >>> 24,  // byte1
-                        npairs >>> 16,  // byte2
-                        npairs >>> 8,   // byte3
-                        npairs);        // byte4
-            
-            // keyed targets:
-            for (int t = 1; t < m_targets.length; ++ t)
-            {
-                final int key = m_keys [t - 1];
-                out.write4 (key >>> 24,  // byte1
-                            key >>> 16,  // byte2
-                            key >>> 8,   // byte3
-                            key);         // byte4
-
-                // key target:
-                emitJumpOffset4 (ctx, ip, m_targets [t]); 
-            }
-        }
-        
-        final int [] m_keys;
-        
-    } // end of nested class
-
-
-    static final class TABLESWITCH extends Branch
-    {
-        TABLESWITCH (final int low, final int high, final int [] targets /* first one is default */)
-        {
-            super (_tableswitch, targets);
-            m_low = low;
-            m_high = high;
-        }
-        
-        int maxlength () { return 12 + (m_targets.length << 2); }
-        
-        void emit (final EmitCtx ctx)
-        {
-            final ByteArrayOStream out = ctx.m_out;
-            final int ip = out.size ();
-            
-            // TODO: switch to long form for any jump > 32k
-            
-            out.write (m_opcode);
-            
-            // padding bytes:
-            for (int p = 0, padCount = 3 - (ip & 3); p < padCount; ++ p) out.write (0);
-             
-            // default:
-            emitJumpOffset4 (ctx, ip, m_targets [0]);
-                        
-            // low, high:
-            final int low = m_low;
-            out.write4 (low >>> 24,  // byte1
-                        low >>> 16,  // byte2
-                        low >>> 8,   // byte3
-                        low);        // byte4
-            
-            final int high = m_high;
-            out.write4 (high >>> 24,  // byte1
-                        high >>> 16,  // byte2
-                        high >>> 8,   // byte3
-                        high);        // byte4
-                        
-            // targets:
-            for (int t = 1; t < m_targets.length; ++ t)
-            {
-                // key target:
-                emitJumpOffset4 (ctx, ip, m_targets [t]); 
-            }
-        }
-            
-        final int m_low, m_high;
-            
-    } // end of nested class
-    
-    
-    /**
-     * TODO: CodeSegment right now must be 100% position-independent code;
-     * otherwise it must follow maxlengtt() Branch pattern... 
-     */
-    static abstract class CodeSegment
-    {
-        CodeSegment (final InstrVisitor visitor)
-        {
-            m_visitor = visitor; // TODO: will this field be used?
-        }
-        
-        abstract int length ();
-        abstract int maxstack ();
-        abstract void emit (EmitCtx ctx);
-        
-        
-        final InstrVisitor m_visitor;
-        
-    } // end of nested class
-    
-    
-    static final class clinitHeader extends CodeSegment
-    {
-        clinitHeader (final InstrVisitor visitor, final int localVarIndex)
-        {
-            super (visitor);
-            final ByteArrayOStream buf = new ByteArrayOStream (CLINIT_HEADER_INIT_CAPACITY); 
-            m_buf = buf;
-            
-            final ClassDef cls = visitor.m_cls;
-            
-            final int [] blockCounts = visitor.m_classBlockCounts;
-            final int instrMethodCount = visitor.m_classInstrMethodCount; // actual number of methods to instrument may be less than the size of the block map 
-            if ($assert.ENABLED) $assert.ASSERT (blockCounts != null && blockCounts.length >= instrMethodCount,
-                "invalid block count map");
-            
-            final int coverageFieldrefIndex = visitor.m_coverageFieldrefIndex;
-            final int preclinitMethodrefIndex = visitor.m_preclinitMethodrefIndex;
-            final int classNameConstantIndex = visitor.m_classNameConstantIndex;
-            
-            if ($assert.ENABLED)
-            {
-                $assert.ASSERT (coverageFieldrefIndex > 0, "invalid coverageFieldrefIndex");
-                $assert.ASSERT (preclinitMethodrefIndex > 0, "invalid registerMethodrefIndex");
-                $assert.ASSERT (classNameConstantIndex > 0, "invalid classNameConstantIndex");
-            }
-
-            // init and load COVERAGE_FIELD:   
-            buf.write3 (_invokestatic,
-                        preclinitMethodrefIndex >>> 8,    // indexbyte1
-                        preclinitMethodrefIndex);         // indexbyte2
-
-            // [stack +1]
-
-            // TODO: disable this when there are no real blocks following?
-            // [in general, use a different template when this method contains a single block]
-
-            // TODO: if this method has been added by us, do not instrument its blocks
-            
-            // push int literal equal to 'methodID' [for the parent method]:
-            CodeGen.push_int_value (buf, cls, visitor.m_methodID);
-            
-            // [stack +2]
-            
-            // push subarray reference:
-            buf.write (_aaload);
-            
-            // [stack +1]
-            
-            // store it in alias var:
-            CodeGen.store_local_object_var (buf, localVarIndex);
-            
-            // [stack +0]            
-        }
-        
-        int length () { return m_buf.size (); }
-        int maxstack () { return 2; } // note: needs to be updated each time emitted code changes
-        
-        void emit (final EmitCtx ctx)
-        {
-            // TODO: better error handling here?
-            try
-            {
-                m_buf.writeTo (ctx.m_out);
-            }
-            catch (IOException ioe)
-            {
-                if ($assert.ENABLED) $assert.ASSERT (false, ioe.toString ());
-            }
-        }
-        
-        
-        private final ByteArrayOStream m_buf;
-        
-        private static final int CLINIT_HEADER_INIT_CAPACITY = 32; // covers about 80% of classes (no reallocation)
-        
-    } // end of nested class
-    
-    
-    static final class methodHeader extends CodeSegment
-    {
-        methodHeader (final InstrVisitor visitor, final int localVarIndex)
-        {
-            super (visitor);
-            final ByteArrayOStream buf = new ByteArrayOStream (HEADER_INIT_CAPACITY);
-            m_buf = buf;
-            
-            final ClassDef cls = visitor.m_cls;
-            final int coverageFieldrefIndex = visitor.m_coverageFieldrefIndex;
-            final int preclinitMethodrefIndex = visitor.m_preclinitMethodrefIndex;
-
-            // TODO: disable this when there are no real blocks following?
-            // [in general, use a different template when this method contains a single block]
-
-            // push ref to the static field and dup it:
-            buf.write4 (_getstatic,
-                        coverageFieldrefIndex >>> 8, // indexbyte1
-                        coverageFieldrefIndex,       // indexbyte2
-                        _dup);
-            
-            // [stack +2]
-            
-            // SF FR 971186: check if it is null and if so run the field
-            // init and class RT register code (only relevant for
-            // methods that can be executed ahead of <clinit>) [rare] 
-            
-            buf.write3 (_ifnonnull, // skip over pre-<clinit> method call
-                        0,
-                        3 + /* size of the block below */ 4);
-                        
-            // [stack +1]
-            
-            // block: call pre-<clinit> method
-            {
-                buf.write4 (_pop,
-                            _invokestatic,
-                            preclinitMethodrefIndex >>> 8,    // indexbyte1
-                            preclinitMethodrefIndex);         // indexbyte2
-                            
-                // [stack +1]
-            }
-
-            // push int literal equal to 'methodID':
-            CodeGen.push_int_value (buf, cls, visitor.m_methodID);
-            
-            // [stack +2]
-            
-            // push subarray reference:
-            buf.write (_aaload);
-            
-            // [stack +1]
-            
-            // store it in alias var:
-            CodeGen.store_local_object_var (buf, localVarIndex);
-            
-            // [stack +0]            
-        }
-        
-        int length () { return m_buf.size (); }
-        int maxstack () { return 2; } // note: needs to be updated each time emitted code changes
-        
-        void emit (final EmitCtx ctx)
-        {
-            // TODO: better error handling here?
-            try
-            {
-                m_buf.writeTo (ctx.m_out);
-            }
-            catch (IOException ioe)
-            {
-                if ($assert.ENABLED) $assert.ASSERT (false, ioe.toString ());
-            }
-        }
-        
-        
-        private final ByteArrayOStream m_buf;
-        
-        private static final int HEADER_INIT_CAPACITY = 16;
-        
-    } // end of nested class
-    
-    
-    static final class BlockSegment extends CodeSegment
-    {
-        public BlockSegment (final InstrVisitor visitor, final int localVarIndex, final int blockID)
-        {
-            super (visitor);
-            final ByteArrayOStream buf = new ByteArrayOStream (BLOCK_INIT_CAPACITY); 
-            m_buf = buf;
-                        
-            final ClassDef cls = visitor.m_cls;
-            
-            // push alias var:
-            CodeGen.load_local_object_var (buf, localVarIndex);
-            
-            // [stack +1]
-            
-            // push int value equal to 'blockID':
-            CodeGen.push_int_value (buf, cls, blockID);
-            
-            // [stack +2]
-            
-            // push boolean 'true':
-            buf.write2 (_iconst_1,
-            
-            // [stack +3]
-            
-            // store it in the array:
-                        _bastore);
-            
-            // [stack +0]
-        }
-        
-        int length () { return m_buf.size (); }
-        int maxstack () { return 3; } // note: needs to be updated each time emitted code changes
-        
-        void emit (final EmitCtx ctx)
-        {
-            // TODO: better error handling here?
-            try
-            {
-                m_buf.writeTo (ctx.m_out);
-            }
-            catch (IOException ioe)
-            {
-                if ($assert.ENABLED) $assert.ASSERT (false, ioe.toString ());
-            }
-        }
-        
-        
-        private final ByteArrayOStream m_buf;
-        
-        private static final int BLOCK_INIT_CAPACITY = 16;
-        
-    } // end of nested class
-    
-    
-    private static final class LineNumberComparator implements Comparator
-    {
-        public final int compare (final Object o1, final Object o2)
-        {
-            return ((LineNumber_info) o1).m_start_pc - ((LineNumber_info) o2).m_start_pc;
-        }
-        
-    } // end of nested class
-  
-  
-  
-    private void setClassName (final String fullName)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (fullName != null && fullName.length () > 0,
-            "null or empty input: fullName");
-        
-        final int lastSlash = fullName.lastIndexOf ('/');
-        if (lastSlash < 0)
-        {
-            m_classPackageName = "";
-            m_className = fullName;
-        }
-        else
-        {
-            if ($assert.ENABLED) $assert.ASSERT (lastSlash < fullName.length () - 1,
-                "malformed class name [" + fullName + "]");
-            
-            m_classPackageName = fullName.substring (0, lastSlash);
-            m_className = fullName.substring (lastSlash + 1);
-        }   
-    }
-    
-    private void consumeSignatureData (final int methodID, final int [] basicBlockOffsets)
-    {
-        // note: by itself, this is not a very good checksum for a class def;
-        // however, it is fast to compute and since it will be used along with
-        // a class name it should be good at detecting structural changes that
-        // matter to us (method and basic block ordering/sizes) 
-        
-        final int temp1 = basicBlockOffsets.length;
-        long temp2 = NBEAST * m_classSignature + (methodID + 1) * temp1;
-        
-        for (int i = 1; i < temp1; ++ i) // skip the initial 0 offset
-        {
-            temp2 = NBEAST * temp2 + basicBlockOffsets [i];
-        }
-        
-        m_classSignature = temp2;
-    }
-     
-    // TODO: use a compilation flag to use table assist here instead of binary search
-    // BETTER YET: use binsearch for online mode and table assist for offline [when memory is not an issue]
-  
-    /**
-     * Returns the maximum index 'i' such that (values[i] <= x). values[]
-     * contains distinct non-negative integers in increasing order. values[0] is 0,
-     * 'x' is non-negative.
-     * 
-     * Edge case:
-     *  returns values.length-1 if values [values.length - 1] < x
-     */
-    private static int lowbound (final int [] values, final int x)
-    {
-        int low = 0, high = values.length - 1;
-        
-        // assertion: lb is in [low, high]
-        
-        while (low <= high)
-        {
-            final int m = (low + high) >> 1;
-            final int v = values [m];
-            
-            if (v == x)
-                return m;
-            else if (v < x)
-                low = m + 1;
-            else // v > x
-                high = m - 1;
-        }
-        
-        return high;
-    }
-    
-    private void reset ()
-    {
-        // TODO: check that all state is reset
-        
-        m_instrument = false;
-        m_metadata = false;
-        m_ignoreAlreadyInstrumented = false;
-        
-        m_cls = null;
-        m_classPackageName = null;
-        m_className = null;
-        m_classSrcFileName = null;
-        m_classBlockMetadata = null;
-        m_classMethodDescriptors = null;
-        
-        m_syntheticStringIndex = -1;
-        m_coverageFieldrefIndex = -1;
-        m_registerMethodrefIndex = -1;
-        m_preclinitMethodrefIndex = -1;
-        m_classNameConstantIndex = -1;
-        m_clinitID = -1;
-        m_clinitStatus = 0;
-        m_classInstrMethodCount = -1;
-        m_classBlockCounts = null;
-        m_classSignature = 0;
-        
-        m_methodID = -1;
-        m_methodName = null;
-        m_methodFirstLine = 0;
-        m_methodBlockOffsets = null;
-        m_methodJumpAdjOffsets = null;
-        m_methodJumpAdjValues = null;
-    }
-    
-    
-    private final boolean m_excludeSyntheticMethods;
-    private final boolean m_excludeBridgeMethods;
-    private final boolean m_doSUIDCompensation;
-    
-    private final Logger m_log; // instr visitor logging context is latched at construction time
-    
-    // non-resettable state:
-    
-    private boolean m_warningIssued;
-    
-    
-    // resettable state:
-    
-    private boolean m_instrument;
-    private boolean m_metadata;
-    private boolean m_ignoreAlreadyInstrumented;
-    
-    /*private*/ ClassDef m_cls;
-    private String m_classPackageName; // in JVM format [com/vladium/...]; empty string for default package
-    private String m_className; // in JVM format [<init>, <clinit>, etc], relative to 'm_classPackageName'
-    private String m_classSrcFileName;
-    private int [][][] m_classBlockMetadata; // methodID->(blockID->line) map [valid only if 'm_constructMetadata' is true; null if the method has not line number table]
-    private MethodDescriptor [] m_classMethodDescriptors;
-    
-    // current class scope: 
-    private int m_syntheticStringIndex;     // index of CONSTANT_Utf8 String that reads "Synthetic"     
-    /*private*/ int m_coverageFieldrefIndex;    // index of the Fieldref for COVERAGE_FIELD
-    private int m_registerMethodrefIndex;   // index of Methodref for RT.r()
-    /*private*/ int m_preclinitMethodrefIndex;  // index of Methodref for pre-<clinit> method
-    /*private*/ int m_classNameConstantIndex;   // index of CONSTANT_String that is the class name [in JVM format]
-    private int m_stampIndex;               // index of CONSTANT_Long that is the class instr stamp
-    private int m_clinitID;                 // offset of <clinit> method [-1 if not determined yet]
-    private int m_clinitStatus;
-    /*private*/ int m_classInstrMethodCount;    // the number of slots in 'm_classBlockCounts' corresponding to methods to be instrumented for coverage
-    /*private*/ int [] m_classBlockCounts;      // basic block counts for all methods [only valid just before <clinit> is processed]
-    private long m_classSignature;
-    
-    // current method scope: 
-    /*private*/ int m_methodID;                 // offset of current method being instrumented
-    private String m_methodName;
-    private int m_methodFirstLine;
-    private int [] m_methodBlockOffsets;    // [unadjusted] basic block boundaries [length = m_classBlockCounts[m_methodID]+1; the last slot is method bytecode length]
-    private int [] m_methodBlockSizes;
-    private int [] m_methodJumpAdjOffsets;    // TODO: length ?
-    private int [] m_methodJumpAdjValues;        // TODO: length ?
-    
-    
-    private static final long NBEAST = 16661; // prime
-
-    private static final String COVERAGE_FIELD_NAME = "$VR" + "c";
-    private static final String SUID_FIELD_NAME = "serialVersionUID";
-    private static final String PRECLINIT_METHOD_NAME = "$VR" + "i";
-
-    private static final String JAVA_IO_SERIALIZABLE_NAME = "java/io/Serializable";
-    private static final String JAVA_IO_EXTERNALIZABLE_NAME = "java/io/Externalizable";
-    
-    private static final int EMIT_CTX_MIN_INIT_CAPACITY = 64; // good value determined empirically
-    private static final int PRECLINIT_INIT_CAPACITY = 128; // covers about 80% of classes (no reallocation)
-    private static final boolean MARK_ADDED_ELEMENTS_SYNTHETIC = true;
-    
-    /* It appears that nested classes and interfaces ought to be marked
-     * as Synthetic; however, neither Sun nor IBM compilers seem to do this.
-     * 
-     * (As a side note, implied no-arg constructors ought to be marked as
-     * synthetic as well, but Sun's javac is not consistent about that either)  
-     */
-    private static final boolean SKIP_SYNTHETIC_CLASSES = false;
-    
-    private static final LineNumberComparator LINE_NUMBER_COMPARATOR = new LineNumberComparator ();
-    
-    private static final byte [] EMPTY_BYTE_ARRAY = new byte [0];
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/instr/instrCommand.java b/core/java12/com/vladium/emma/instr/instrCommand.java
deleted file mode 100644
index eb25312..0000000
--- a/core/java12/com/vladium/emma/instr/instrCommand.java
+++ /dev/null
@@ -1,211 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: instrCommand.java,v 1.1.1.1.2.1 2004/07/16 23:32:04 vlad_r Exp $
- */
-package com.vladium.emma.instr;
-
-import java.io.IOException;
-
-import com.vladium.util.ClassLoaderResolver;
-import com.vladium.util.args.IOptsParser;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.Command;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMARuntimeException;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class instrCommand extends Command
-{
-    // public: ................................................................
-
-    public instrCommand (final String usageToolName, final String [] args)
-    {
-        super (usageToolName, args);
-        
-        m_outMode = InstrProcessor.OutMode.OUT_MODE_COPY; // default
-    }
-
-    public synchronized void run ()
-    {
-        ClassLoader loader;
-        try
-        {
-            loader = ClassLoaderResolver.getClassLoader ();
-        }
-        catch (Throwable t)
-        {
-            loader = getClass ().getClassLoader ();
-        }
-                
-        try
-        {
-            // process 'args':
-            {
-                final IOptsParser parser = getOptParser (loader);
-                final IOptsParser.IOpts parsedopts = parser.parse (m_args);
-                
-                // check if usage is requested before checking args parse errors etc:
-                {
-                    final int usageRequestLevel = parsedopts.usageRequestLevel ();
-
-                    if (usageRequestLevel > 0)
-                    {
-                        usageexit (parser, usageRequestLevel, null);
-                        return;
-                    }
-                }
-                
-                final IOptsParser.IOpt [] opts = parsedopts.getOpts ();
-                
-                if (opts == null) // this means there were args parsing errors
-                {
-                    parsedopts.error (m_out, STDOUT_WIDTH);
-                    usageexit (parser, IOptsParser.SHORT_USAGE, null);
-                    return;
-                }
-                
-                // process parsed args:              
-                try
-                {
-                    for (int o = 0; o < opts.length; ++ o)
-                    {
-                        final IOptsParser.IOpt opt = opts [o];
-                        final String on = opt.getCanonicalName ();
-                        
-                        if (! processOpt (opt))
-                        {
-                            if ("ip".equals (on))
-                            {
-                                m_instrpath = getListOptValue (opt, PATH_DELIMITERS, true);
-                            }
-                            else if ("d".equals (on))
-                            {
-                                m_outDirName = opt.getFirstValue ();
-                            }
-                            else if ("out".equals (on))
-                            {
-                                m_outFileName = opt.getFirstValue ();
-                            }
-                            else if ("merge".equals (on))
-                            {
-                                m_outDataMerge = getOptionalBooleanOptValue (opt) ? Boolean.TRUE : Boolean.FALSE; 
-                            }
-                            else if ("ix".equals (on))
-                            {
-                                // note: this allows path delimiter in the pattern list as well
-                                m_ixpath = getListOptValue (opt, COMMA_DELIMITERS, true);
-                            }
-                            else if ("m".equals (on))
-                            {
-                                final String ov = opt.getFirstValue ();
-                                
-                                final InstrProcessor.OutMode outMode = InstrProcessor.OutMode.nameToMode (ov);
-                                if (outMode == null)
-                                {
-                                    usageexit (parser, IOptsParser.SHORT_USAGE,
-                                        "invalid '" + opts [o].getName () + "' option value: " + ov);
-                                    return;
-                                }
-                                m_outMode = outMode;
-                            }
-                        }
-                    }
-
-                    // user '-props' file property overrides:
-                    
-                    if (! processFilePropertyOverrides ()) return;
-                    
-                    // process prefixed opts:
-                    
-                    processCmdPropertyOverrides (parsedopts);
-                }
-                catch (IOException ioe)
-                {
-                    throw new EMMARuntimeException (IAppErrorCodes.ARGS_IO_FAILURE, ioe);
-                }
-                
-                // handle cmd line-level defaults:
-                {
-                    if ($assert.ENABLED) $assert.ASSERT (m_outMode != null, "m_outMode not set");
-                    
-                    if ((m_outMode != InstrProcessor.OutMode.OUT_MODE_OVERWRITE) && (m_outDirName == null))
-                    {
-                        usageexit (parser, IOptsParser.SHORT_USAGE,
-                            "output directory must be specified for '" + m_outMode + "' output mode");
-                        return;
-                    }
-                }
-            }
-            
-            // run the instrumentor:
-            {
-                final InstrProcessor processor = InstrProcessor.create ();
-                processor.setAppName (IAppConstants.APP_NAME); // for log prefixing
-                
-                processor.setInstrPath (m_instrpath, true); // TODO: an option to set 'canonical'?
-                processor.setInclExclFilter (m_ixpath);
-                $assert.ASSERT (m_outMode != null, "m_outMode not set");
-                processor.setOutMode (m_outMode);
-                processor.setInstrOutDir (m_outDirName);
-                processor.setMetaOutFile (m_outFileName);
-                processor.setMetaOutMerge (m_outDataMerge);
-                processor.setPropertyOverrides (m_propertyOverrides);
-                
-                processor.run ();
-            }
-        }
-        catch (EMMARuntimeException yre)
-        {
-            // TODO: see below
-            
-            exit (true, yre.getMessage (), yre, RC_UNEXPECTED); // does not return
-            return;
-        }
-        catch (Throwable t)
-        {
-            // TODO: embed: OS/JVM fingerprint, build #, etc
-            // TODO: save stack trace in a file and prompt user to send it to ...
-            
-            exit (true, "unexpected failure: ", t, RC_UNEXPECTED); // does not return
-            return;
-        }
-
-        exit (false, null, null, RC_OK);
-    }    
-    
-    // protected: .............................................................
-
-
-    protected void initialize ()
-    {
-        super.initialize ();
-    }
-    
-    protected String usageArgsMsg ()
-    {
-        return "[options]";
-    }
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-        
-    private String [] m_instrpath;
-    private String [] m_ixpath;
-    private String m_outDirName;
-    private String m_outFileName;
-    private Boolean m_outDataMerge;
-    private InstrProcessor.OutMode m_outMode;
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/AbstractItemVisitor.java b/core/java12/com/vladium/emma/report/AbstractItemVisitor.java
deleted file mode 100644
index a63176a..0000000
--- a/core/java12/com/vladium/emma/report/AbstractItemVisitor.java
+++ /dev/null
@@ -1,52 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AbstractItemVisitor.java,v 1.1.1.1 2004/05/09 16:57:36 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class AbstractItemVisitor implements IItemVisitor
-{
-    // public: ................................................................
-
-    public Object visit (final AllItem item, final Object ctx)
-    {
-        return ctx;
-    }
-
-    public Object visit (final PackageItem item, final Object ctx)
-    {
-        return ctx;
-    }
-
-    public Object visit (final SrcFileItem item, final Object ctx)
-    {
-        return ctx;
-    }
-
-    public Object visit (final ClassItem item, final Object ctx)
-    {
-        return ctx;
-    }
-
-    public Object visit (final MethodItem item, final Object ctx)
-    {
-        return ctx;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/AbstractReportGenerator.java b/core/java12/com/vladium/emma/report/AbstractReportGenerator.java
deleted file mode 100644
index 6e37179..0000000
--- a/core/java12/com/vladium/emma/report/AbstractReportGenerator.java
+++ /dev/null
@@ -1,258 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AbstractReportGenerator.java,v 1.1.1.1.2.4 2005/04/24 23:51:37 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.util.Iterator;
-import java.util.Set;
-import java.util.TreeSet;
-
-import com.vladium.logging.Logger;
-import com.vladium.util.Descriptors;
-import com.vladium.util.IProperties;
-import com.vladium.util.IntIntMap;
-import com.vladium.util.IntVector;
-import com.vladium.util.ObjectIntMap;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.data.ClassDescriptor;
-import com.vladium.emma.data.ICoverageData;
-import com.vladium.emma.data.IMetaData;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class AbstractReportGenerator extends AbstractItemVisitor
-                                       implements IReportGenerator
-{
-    // public: ................................................................
-    
-    
-    public static IReportGenerator create (final String type)
-    {
-        if ((type == null) || (type.length () == 0))
-            throw new IllegalArgumentException ("null/empty input: type");
-        
-        // TODO: proper pluggability pattern here
-        
-        if ("html".equals (type))
-            return new com.vladium.emma.report.html.ReportGenerator ();
-        else if ("txt".equals (type))
-            return new com.vladium.emma.report.txt.ReportGenerator ();
-        else if ("xml".equals (type))
-            return new com.vladium.emma.report.xml.ReportGenerator ();
-        else // TODO: error code
-            throw new EMMARuntimeException ("no report generator class found for type [" + type + "]");
-    }
-    
-    
-    public void initialize (final IMetaData mdata, final ICoverageData cdata,
-                            final SourcePathCache cache, final IProperties properties)
-        throws EMMARuntimeException
-    {
-        m_log = Logger.getLogger ();
-        m_verbose = m_log.atVERBOSE ();
-        
-        m_settings = ReportProperties.parseProperties (properties, getType ());
-        
-        m_cache = cache;
-                
-        m_hasSrcFileInfo = mdata.hasSrcFileData ();
-        m_hasLineNumberInfo = mdata.hasLineNumberData ();
-        
-        boolean debugInfoWarning = false;
-        boolean bailOut = false;
-        
-        // src view is not possible if 'm_hasSrcFileInfo' is false:        
-        if (! mdata.hasSrcFileData () && (m_settings.getViewType () == IReportDataView.HIER_SRC_VIEW))
-        {
-            debugInfoWarning = true;
-            
-            m_log.warning ("not all instrumented classes were compiled with source file");
-            m_log.warning ("debug data: no sources will be embedded in the report.");
-            
-            m_settings.setViewType (IReportDataView.HIER_CLS_VIEW);
-        }
-        
-        // line coverage column must be removed if 'm_hasLineNumberInfo' is false:
-        if (! m_hasLineNumberInfo)
-        {
-            final int [] userColumnIDs = m_settings.getColumnOrder ();
-            final IntVector columnIDs = new IntVector ();
-            
-            boolean removed = false;
-            for (int c = 0; c < userColumnIDs.length; ++ c)
-            {
-                if (userColumnIDs [c] == IItemAttribute.ATTRIBUTE_LINE_COVERAGE_ID)
-                    removed = true;
-                else
-                    columnIDs.add (userColumnIDs [c]);
-            }
-            
-            // at this point it is possible that there are no columns left: bail out
-            if (removed)
-            {
-                debugInfoWarning = true;
-                
-                if (columnIDs.size () == 0)
-                {
-                    m_log.warning ("line coverage requested in a report of type [" + getType () + "] but");
-                    m_log.warning ("not all instrumented classes were compiled with line number");
-                    m_log.warning ("debug data: since this was the only requested column, no report will be generated.");
-
-                    bailOut = true;
-                }
-                else
-                {
-                    m_log.warning ("line coverage requested in a report of type [" + getType () + "] but");
-                    m_log.warning ("not all instrumented classes were compiled with line number");
-                    m_log.warning ("debug data: this column will be removed from the report.");
-                    
-                    m_settings.setColumnOrder (columnIDs.values ());
-                    
-                    final int [] userSort = m_settings.getSortOrder ();
-                    final IntVector sort = new IntVector ();
-                    
-                    for (int c = 0; c < userSort.length; c += 2)
-                    {
-                        if (Math.abs (userSort [c]) != IItemAttribute.ATTRIBUTE_LINE_COVERAGE_ID)
-                        {
-                            sort.add (userSort [c]);
-                            sort.add (userSort [c + 1]);
-                        }
-                    }
-                    
-                    m_settings.setSortOrder (sort.values ());
-                }
-            }
-        }
-        // note: no need to adjust m_metrics due to possible column removal above
-        
-        // SF FR 971176: provide user with sample classes that caused the above warnings
-        if (debugInfoWarning && m_log.atINFO ())
-        {
-            final Set /* String */ sampleClassNames = new TreeSet ();
-            final ObjectIntMap /* packageVMName:String -> count:int */ countMap = new ObjectIntMap ();
-            final int [] _count = new int [1];
-            
-            for (Iterator /* ClassDescriptor */ descriptors = mdata.iterator (); descriptors.hasNext (); )
-            {    
-                final ClassDescriptor cls = (ClassDescriptor) descriptors.next ();
-                
-                // SF BUG 979717: this check was incorrectly absent in the initial FR impl:
-                if (! cls.hasCompleteLineNumberInfo () || ! cls.hasSrcFileInfo ())
-                {
-                    final String packageVMName = cls.getPackageVMName ();
-                    final int count = countMap.get (packageVMName, _count)
-                        ? _count [0]
-                        : 0;
-                    
-                    if (count < MAX_DEBUG_INFO_WARNING_COUNT)
-                    {
-                        sampleClassNames.add (Descriptors.vmNameToJavaName (cls.getClassVMName ()));
-                        countMap.put (packageVMName, count + 1);
-                    }
-                }
-            }
-            
-            m_log.info ("showing up to " + MAX_DEBUG_INFO_WARNING_COUNT + " classes without full debug info per package:");
-            for (Iterator /* String */ names = sampleClassNames.iterator (); names.hasNext (); )
-            {
-                m_log.info ("  " + names.next ());
-            }
-        }
-        
-        if (bailOut)
-        {
-            // TODO: error code
-            throw new EMMARuntimeException ("BAILED OUT");
-        }
-        
-        final IItemMetadata [] allTypes = IItemMetadata.Factory.getAllTypes ();
-        m_typeSortComparators = new ItemComparator [allTypes.length];
-        
-        for (int t = 0; t < allTypes.length; ++ t)
-        {
-            final IntVector orderedAttrIDsWithDir = new IntVector ();
-            final long typeAttrIDSet = allTypes [t].getAttributeIDs ();
-            
-            for (int s = 0; s < m_settings.getSortOrder ().length; s += 2)
-            {
-                final int attrID = m_settings.getSortOrder () [s];
-                
-                if ((typeAttrIDSet & (1 << attrID)) != 0)
-                {
-                    orderedAttrIDsWithDir.add (attrID);
-                    
-                    final int dir = m_settings.getSortOrder () [s + 1];
-                    orderedAttrIDsWithDir.add (dir);
-                }
-            }
-            
-            m_typeSortComparators [t] = ItemComparator.Factory.create (orderedAttrIDsWithDir.values (), m_settings.getUnitsType ());
-        }
-        
-        m_metrics = new int [allTypes.length];
-        final IntIntMap metrics = m_settings.getMetrics ();
-        for (int t = 0; t < m_metrics.length; ++ t)
-        {
-            m_metrics [t] = -1;
-            metrics.get (t, m_metrics, t);
-        }
-        
-        final IReportDataModel model = IReportDataModel.Factory.create (mdata, cdata);
-        m_view = model.getView (m_settings.getViewType ());
-        
-        m_srcView = (m_settings.getViewType () == IReportDataView.HIER_SRC_VIEW);
-    }
-    
-    public void cleanup ()
-    {
-        reset ();
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected void reset ()
-    {
-        m_settings = null;
-        m_cache = null;
-        m_view = null;
-        m_srcView = false;
-        
-        //m_typeSortIDs = null;
-        m_typeSortComparators = null;
-        m_metrics = null;
-        
-        m_log = null;
-    }
-    
-
-    protected ReportProperties.ParsedProperties m_settings;
-    protected SourcePathCache m_cache;
-    protected IReportDataView m_view;
-    protected boolean m_srcView;
-    
-    protected boolean m_hasSrcFileInfo, m_hasLineNumberInfo;
-    protected ItemComparator [] m_typeSortComparators; // m_typeSortComparators [t] is a comparator representing the sort order for item type t 
-    protected int [] m_metrics; // -1 means no pass/fail check for this attribute
-    
-    protected Logger m_log; // every report generator is used on a single thread but the logger needs to be run()-scoped
-    protected boolean m_verbose;
-    
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final int MAX_DEBUG_INFO_WARNING_COUNT = 3; // per package
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/AllItem.java b/core/java12/com/vladium/emma/report/AllItem.java
deleted file mode 100644
index 46ce575..0000000
--- a/core/java12/com/vladium/emma/report/AllItem.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AllItem.java,v 1.1.1.1 2004/05/09 16:57:36 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class AllItem extends Item
-{
-    // public: ................................................................
-    
-    public AllItem ()
-    {
-        super (null);
-    }
-    
-    public String getName ()
-    {
-        return "all classes";
-    }
-        
-    public void accept (final IItemVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    // TODO: remove these instance methods returning static data
-    public final IItemMetadata getMetadata ()
-    {
-        return METADATA;
-    }
-
-    public static IItemMetadata getTypeMetadata ()
-    {
-        return METADATA;
-    }
-        
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final Item.ItemMetadata METADATA; // set in <clinit>
-        
-    static
-    {        
-        METADATA = new Item.ItemMetadata (IItemMetadata.TYPE_ID_ALL, "all",
-            1 << IItemAttribute.ATTRIBUTE_NAME_ID |
-            1 << IItemAttribute.ATTRIBUTE_CLASS_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_METHOD_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_BLOCK_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_LINE_COVERAGE_ID);
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/ClassItem.java b/core/java12/com/vladium/emma/report/ClassItem.java
deleted file mode 100644
index f3423cf..0000000
--- a/core/java12/com/vladium/emma/report/ClassItem.java
+++ /dev/null
@@ -1,246 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ClassItem.java,v 1.1.1.1.2.1 2004/06/20 20:07:22 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.util.Iterator;
-
-import com.vladium.util.IntObjectMap;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.data.ClassDescriptor;
-import com.vladium.emma.data.MethodDescriptor;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class ClassItem extends Item
-{
-    // public: ................................................................
-    
-    public ClassItem (final IItem parent, final ClassDescriptor cls, final boolean [][] coverage)
-    {
-        super (parent);
-        
-        m_cls = cls;
-        m_coverage = coverage;
-    }
-    
-    public String getName ()
-    {
-        return m_cls.getName ();
-    }
-    
-    public String getSrcFileName ()
-    {
-        return m_cls.getSrcFileName ();
-    }
-    
-    // TODO: SrcFileItem could benefit from this method for its own getFirstLine()
-    public int getFirstLine ()
-    {
-        // TODO: state validation
-        
-        if (m_firstLine == 0)
-        {
-            final MethodDescriptor [] methods = m_cls.getMethods ();
-            
-            int firstLine = Integer.MAX_VALUE;
-            for (int m = 0, mLimit = methods.length; m < mLimit; ++ m)
-            {
-                final int mFirstLine = methods [m].getFirstLine ();
-                if ((mFirstLine > 0) && (mFirstLine < firstLine))
-                    firstLine = mFirstLine;
-            }
-            
-            m_firstLine = firstLine;
-            return firstLine;
-        }
-        
-        return m_firstLine;
-    }
-        
-    public ClassDescriptor getClassDescriptor ()
-    {
-        return m_cls;
-    }
-    
-    public boolean [][] getCoverage ()
-    {
-        return m_coverage;
-    }
-    
-    public boolean loaded ()
-    {
-        return m_coverage != null;
-    }
-    
-    public int getAggregate (final int type)
-    {
-        final int [] aggregates = m_aggregates;
-
-        int value = aggregates [type];
-        
-        if (value < 0)
-        {
-            switch (type)
-            {
-                case COVERAGE_CLASS_COUNT:
-                case    TOTAL_CLASS_COUNT:
-                {
-                    aggregates [TOTAL_CLASS_COUNT] = 1;
-                    aggregates [COVERAGE_CLASS_COUNT] = m_coverage != null ? 1 : 0;
-                    
-                    return aggregates [type];
-                }
-                //break;
-           
-           
-                case COVERAGE_LINE_COUNT:
-                case    TOTAL_LINE_COUNT:
-                
-                case COVERAGE_LINE_INSTR:
-                {
-                    // line aggregate types are special when used on clsfile items:
-                    // unlike all others, they do not simply add up when the line
-                    // info is available; instead, lines from all methods belonging
-                    // to the same clsfile parent are set-merged 
-                    
-                    final boolean [][] ccoverage = m_coverage; // this can be null
-                    
-                    final IntObjectMap /* line -> int[2] */ cldata = new IntObjectMap ();
-                    final MethodDescriptor [] methoddescs = m_cls.getMethods ();
-                        
-                    for (Iterator methods = getChildren (); methods.hasNext (); )
-                    {
-                        final MethodItem method = (MethodItem) methods.next ();
-                        final int methodID = method.getID ();
-                        
-                        final boolean [] mcoverage = ccoverage == null ? null : ccoverage [methodID];
-                        
-                        final MethodDescriptor methoddesc = methoddescs [methodID];                        
-                        final int [] mbsizes = methoddesc.getBlockSizes ();
-                        final IntObjectMap mlineMap = methoddesc.getLineMap ();
-                        if ($assert.ENABLED) $assert.ASSERT (mlineMap != null);
-                        
-
-                        final int [] mlines = mlineMap.keys ();
-                        for (int ml = 0, mlLimit = mlines.length; ml < mlLimit; ++ ml)
-                        {
-                            final int mline = mlines [ml];
-                            
-                            int [] data = (int []) cldata.get (mline);
-                            if (data == null)
-                            {
-                                data = new int [4]; // { totalcount, totalinstr, coveragecount, coverageinstr }
-                                cldata.put (mline, data);
-                            }
-                            
-                            final int [] lblocks = (int []) mlineMap.get (mline);
-                            
-                            final int bCount = lblocks.length; 
-                            data [0] += bCount;
-                            
-                            for (int bID = 0; bID < bCount; ++ bID)
-                            {
-                                final int block = lblocks [bID];
-                                
-                                final boolean bcovered = mcoverage != null && mcoverage [block];
-                                final int instr = mbsizes [block];
-                                
-                                data [1] += instr;
-                                if (bcovered)
-                                {
-                                    ++ data [2];
-                                    data [3] += instr;
-                                }
-                            }
-                        }
-                    }
-                    
-                    aggregates [TOTAL_LINE_COUNT] = cldata.size ();
-                    
-                    int coverageLineCount = 0;
-                    int coverageLineInstr = 0;
-                    
-                    final int [] clines = cldata.keys ();
-                    for (int cl = 0, clLimit = clines.length; cl < clLimit; ++ cl)
-                    {
-                        final int cline = clines [cl];
-                        final int [] data = (int []) cldata.get (cline);
-                        
-                        final int ltotalCount = data [0];
-                        final int ltotalInstr = data [1];
-                        final int lcoverageCount = data [2];
-                        final int lcoverageInstr = data [3];
-                        
-                        if (lcoverageInstr > 0)
-                        {
-                            coverageLineCount += (PRECISION * lcoverageCount) / ltotalCount;
-                            coverageLineInstr += (PRECISION * lcoverageInstr) / ltotalInstr;
-                        }
-                    }
-                    
-                    aggregates [COVERAGE_LINE_COUNT] = coverageLineCount;
-                    aggregates [COVERAGE_LINE_INSTR] = coverageLineInstr;
-                    
-                    return aggregates [type];
-                }
-                //break;
-                
-                               
-                default: return super.getAggregate (type);
-            }
-        }
-        
-        return value;
-    }
-    
-    public void accept (final IItemVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public final IItemMetadata getMetadata ()
-    {
-        return METADATA;
-    }
-    
-    public static IItemMetadata getTypeMetadata ()
-    {
-        return METADATA;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    final ClassDescriptor m_cls;
-    final boolean [][] m_coverage;
-    
-    // private: ...............................................................
-    
-    
-    private int m_firstLine;
-    
-    private static final Item.ItemMetadata METADATA; // set in <clinit>
-        
-    static
-    {
-        METADATA = new Item.ItemMetadata (IItemMetadata.TYPE_ID_CLASS, "class",
-            1 << IItemAttribute.ATTRIBUTE_NAME_ID |
-            1 << IItemAttribute.ATTRIBUTE_CLASS_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_METHOD_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_BLOCK_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_LINE_COVERAGE_ID);
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/IItem.java b/core/java12/com/vladium/emma/report/IItem.java
deleted file mode 100644
index 4d5bed3..0000000
--- a/core/java12/com/vladium/emma/report/IItem.java
+++ /dev/null
@@ -1,75 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IItem.java,v 1.1.1.1.2.1 2005/06/12 22:43:11 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.util.Iterator;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IItem
-{
-    // public: ................................................................
-    
-    // TODO: consider making this an abstact class [merge into Item]
-    
-    // note: this design does not enforce all items at the same level being of the same 'type' (class, pkg, method, etc)    
-
-    IItem getParent ();
-    int getChildCount ();
-    Iterator /* IItem */ getChildren ();
-    /**
-     * 
-     * @param order [null is equivalent to no sort]
-     * @return
-     */
-    Iterator /* IItem */ getChildren (ItemComparator /* IItem */ order);
-    
-    String getName ();   
-    IItemMetadata getMetadata ();
-    IItemAttribute getAttribute (int attributeID, int unitsID);
-    int getAggregate (int type);
-    
-    void accept (IItemVisitor visitor, Object ctx);
-
-
-    // TODO: move these elsewhere and fix gaps
-        // WARNING: careful about reordering!
-    
-        // (coverage data) measured in counts:
-        int COVERAGE_CLASS_COUNT    = 5; // count of class loads
-        int COVERAGE_METHOD_COUNT   = 4; // count of method entries
-        
-        // (coverage data) measured in counts or instrs:
-        int COVERAGE_BLOCK_COUNT    = 0; // in count units
-        int COVERAGE_LINE_COUNT     = 1; // in count units
-        int COVERAGE_BLOCK_INSTR    = 2; // in instr units
-        int COVERAGE_LINE_INSTR     = 3; // total line instr coverage, scaled up by PRECISION
-        
-    
-        // (metadata) measured in counts:
-        int TOTAL_CLASS_COUNT       = 11;
-        int TOTAL_METHOD_COUNT      = 10;
-    
-        // (metadata) measured in counts or instrs:
-        int TOTAL_BLOCK_COUNT       = 6; // in count units
-        int TOTAL_LINE_COUNT        = 7; // in count units
-        int TOTAL_BLOCK_INSTR       = 8; // in instr units
-        //int TOTAL_LINE_INSTR        = 9; // in instr units
-       
-        int TOTAL_SRCFILE_COUNT     = 12;
-        //int TOTAL_SRCLINE_COUNT     = 13;
-        
-        int NUM_OF_AGGREGATES = TOTAL_SRCFILE_COUNT + 1;
-        int PRECISION = 100; // BUG_SF988160: increase overflow safety margin for very large projects  
-   
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/IItemAttribute.java b/core/java12/com/vladium/emma/report/IItemAttribute.java
deleted file mode 100644
index 1d8777d..0000000
--- a/core/java12/com/vladium/emma/report/IItemAttribute.java
+++ /dev/null
@@ -1,266 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IItemAttribute.java,v 1.1.1.1.2.1 2004/07/10 19:08:50 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.text.DecimalFormat;
-import java.text.FieldPosition;
-import java.text.NumberFormat;
-import java.util.Comparator;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IItemAttribute
-{
-    // public: ................................................................
-    
-    // TODO: this modeling (units is an independent axis) is not ideal, because
-    // not all of the attributes have meaningful separation by unit type
-    
-    // note: the ordering is consistent with code in Factory:
-    
-    int ATTRIBUTE_NAME_ID               = 0;
-    int ATTRIBUTE_CLASS_COVERAGE_ID     = 1;
-    int ATTRIBUTE_METHOD_COVERAGE_ID    = 2;
-    int ATTRIBUTE_BLOCK_COVERAGE_ID     = 3;
-    int ATTRIBUTE_LINE_COVERAGE_ID      = 4;
-    
-    // note: the ordering is consistent with code in Factory and SrcFileItem:
-    
-    int UNITS_COUNT = 0;
-    int UNITS_INSTR = 1;    
-    
-    Comparator /* IItem */ comparator ();
-    String getName ();
-    void format (IItem item, StringBuffer appendTo);
-    boolean passes (IItem item, int criterion); // ideally, criteria should come from a double-dispatched API
-    
-    
-    abstract class Factory
-    {
-        public static IItemAttribute getAttribute (final int attributeID, final int unitsID)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (attributeID >= ATTRIBUTE_NAME_ID && attributeID <= ATTRIBUTE_LINE_COVERAGE_ID, "invalid attribute ID: " + attributeID);
-            if ($assert.ENABLED) $assert.ASSERT (unitsID >= UNITS_COUNT && unitsID <= UNITS_INSTR, "invalid units ID: " + unitsID);
-            
-            return ATTRIBUTES [unitsID][attributeID];
-        }
-        
-        public static IItemAttribute [] getAttributes (final int unitsID)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (unitsID >= UNITS_COUNT && unitsID <= UNITS_INSTR, "invalid units ID: " + unitsID);
-            
-            return (IItemAttribute []) ATTRIBUTES [unitsID].clone ();
-        }
-        
-        private static abstract class Attribute implements IItemAttribute
-        {
-            public String getName ()
-            {
-                return m_name;
-            }
-            
-             protected Attribute (final String name)
-            {
-                if (name == null) throw new IllegalArgumentException ("null input: name");
-                
-                m_name = name;
-            }
-
-            
-            private final String m_name;
-            
-        } // end of nested class
-        
-        
-        private static final class NameAttribute extends Attribute
-                                                 implements IItemAttribute
-        {
-            public Comparator comparator ()
-            {
-                return m_comparator;
-            }  
-    
-            public void format (final IItem item, final StringBuffer appendTo)
-            {
-                appendTo.append (item.getName ());
-            }
-            
-            public boolean passes (final IItem item, final int criterion)
-            {
-                return true; // names always pass [for now]
-            }
-
-            
-            private static final class NameComparator implements Comparator
-            {
-                public int compare (final Object l, final Object g)
-                {
-                    final IItem il = (IItem) l;
-                    final IItem ig = (IItem) g;
-                                        
-                    return il.getName ().compareTo (ig.getName ());
-                }
-
-            } // end of nested class
-            
-            NameAttribute (final String name)
-            {
-                super (name);
-                
-                m_comparator = new NameComparator ();
-            }
-            
-            
-            private final Comparator m_comparator;
-            
-        } // end of nested class
-        
-        
-        private static final class FractionAttribute extends Attribute
-                                                     implements IItemAttribute
-        {
-            public Comparator comparator ()
-            {
-                return m_comparator;
-            }  
-    
-            public void format (final IItem item, final StringBuffer appendTo)
-            {
-                final int n = item.getAggregate (m_numeratorAggregateID);
-                final double n_scaled = (double) n / m_scale;
-                final int d = item.getAggregate (m_denominatorAggregateID);
-                
-                // d can be 0 legally: the compiler can generate classes with no methods in them [happens with synthetic classes, for example]
-                //if ($assert.ENABLED) $assert.ASSERT (d > 0, "[attr ID = " + m_denominatorAggregateID + "] invalid denominator: " + d);
-
-                final int appendToStart = appendTo.length ();
-
-                if (d == 0)
-                    m_format.format (1.0F, appendTo, m_fieldPosition);
-                else
-                    m_format.format (n_scaled / d, appendTo, m_fieldPosition);
-                
-                final int iLimit = Math.max (1, 5 - appendTo.length () + appendToStart);
-                for (int i = 0; i < iLimit; ++ i) appendTo.append (' ');
-                
-                appendTo.append ('(');
-                m_nFormat.format (n_scaled, appendTo, m_fieldPosition);
-                appendTo.append ('/');
-                appendTo.append (d);
-                appendTo.append (')');
-            }
-            
-            public boolean passes (final IItem item, final int criterion)
-            {
-                final int n = item.getAggregate (m_numeratorAggregateID);
-                final int d = item.getAggregate (m_denominatorAggregateID);
-                
-                return ((double) n) * IItem.PRECISION >=  ((double) d) * m_scale * criterion; 
-            }
-            
-            
-            private final class FractionComparator implements Comparator
-            {
-                public int compare (final Object l, final Object g)
-                {
-                    final IItem il = (IItem) l;
-                    final IItem ig = (IItem) g;
-                    
-                    final double nil = il.getAggregate (m_numeratorAggregateID);
-                    final double dil = il.getAggregate (m_denominatorAggregateID);
-                    
-                    final double nig = ig.getAggregate (m_numeratorAggregateID);
-                    final double dig = ig.getAggregate (m_denominatorAggregateID);
-                    
-                    final double diff = nil * dig - nig * dil; 
-
-                    return diff > 0.0 ? +1 : (diff < 0.0 ? -1 : 0);
-                }
-                
-            } // end of inner class
-            
-            
-            FractionAttribute (final String name, final int numeratorAggregateID, final int denominatorAggregateID, final int scale, final int nFractionDigits)
-            {
-                super (name);
-                
-                if ($assert.ENABLED) $assert.ASSERT (scale != 0, "scale: " + scale);
-
-                m_numeratorAggregateID = numeratorAggregateID;
-                m_denominatorAggregateID = denominatorAggregateID; // ok to be zero
-                m_scale = scale;
-                
-                m_format = (DecimalFormat) NumberFormat.getPercentInstance (); // TODO: locale
-                m_fieldPosition = new FieldPosition (DecimalFormat.INTEGER_FIELD);
-                
-                // TODO: set this from a pattern property
-                //m_format.setMinimumFractionDigits (1);
-                m_format.setMaximumFractionDigits (0);
-                //m_format.setDecimalSeparatorAlwaysShown (false);
-                
-                m_nFormat = (DecimalFormat) NumberFormat.getInstance (); // TODO: locale
-                m_nFormat.setGroupingUsed (false);
-                m_nFormat.setMaximumFractionDigits (nFractionDigits);
-                
-                m_comparator = new FractionComparator ();
-            }
-            
-            
-            final int m_numeratorAggregateID, m_denominatorAggregateID;
-            
-            private final int m_scale;
-            private final DecimalFormat m_format, m_nFormat;
-            private final FieldPosition m_fieldPosition;
-            private final Comparator m_comparator; 
-            
-        } // end of nested class
-
-
-
-        private Factory () {}
-        
-        private static final IItemAttribute [/* unit */][/* attributes */] ATTRIBUTES; // set in <clinit> 
-        
-        static
-        {
-            final IItemAttribute nameAttribute = new NameAttribute ("name");
-            
-            final IItemAttribute classCoverageAttribute = new FractionAttribute ("class, %", IItem.COVERAGE_CLASS_COUNT, IItem.TOTAL_CLASS_COUNT, 1, 0);
-            final IItemAttribute methodCoverageAttribute = new FractionAttribute ("method, %", IItem.COVERAGE_METHOD_COUNT, IItem.TOTAL_METHOD_COUNT, 1, 0);
-            
-            ATTRIBUTES = new IItemAttribute [][]
-            {
-                /* count: */
-                {
-                    nameAttribute,
-                    classCoverageAttribute,
-                    methodCoverageAttribute,
-                    new FractionAttribute ("block, %", IItem.COVERAGE_BLOCK_COUNT, IItem.TOTAL_BLOCK_COUNT, 1, 0),
-                    new FractionAttribute ("line, %", IItem.COVERAGE_LINE_COUNT, IItem.TOTAL_LINE_COUNT, IItem.PRECISION, 1),
-                },
-                /* instr: */
-                {
-                    nameAttribute,
-                    classCoverageAttribute,
-                    methodCoverageAttribute,
-                    new FractionAttribute ("block, %", IItem.COVERAGE_BLOCK_INSTR, IItem.TOTAL_BLOCK_INSTR, 1, 0),
-                    new FractionAttribute ("line, %", IItem.COVERAGE_LINE_INSTR, IItem.TOTAL_LINE_COUNT, IItem.PRECISION, 1),
-                },
-            };
-        }
-        
-    } // end of nested class
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/IItemMetadata.java b/core/java12/com/vladium/emma/report/IItemMetadata.java
deleted file mode 100644
index e0f3e50..0000000
--- a/core/java12/com/vladium/emma/report/IItemMetadata.java
+++ /dev/null
@@ -1,76 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IItemMetadata.java,v 1.1.1.1 2004/05/09 16:57:37 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IItemMetadata
-{
-    // public: ................................................................
-
-    // note: order is in sync with Factory init code    
-    int TYPE_ID_ALL         = 0;
-    int TYPE_ID_PACKAGE     = 1;
-    int TYPE_ID_SRCFILE     = 2;
-    int TYPE_ID_CLASS       = 3;
-    int TYPE_ID_METHOD      = 4;
-    
-    int getTypeID ();
-    String getTypeName ();
-    
-    /**
-     * Using a long is only ok for less than 64 global attributes, but this limit
-     * seems ok for a long time to come. 
-     * 
-     * @return bitmask for valid attributes
-     */
-    long getAttributeIDs ();
-    
-    abstract class Factory
-    {
-        public static IItemMetadata getTypeMetadata (final int typeID)
-        {
-            if ((typeID < TYPE_ID_ALL) || (typeID > TYPE_ID_METHOD))
-                throw new IllegalArgumentException ("invalid type ID: " + typeID);
-                
-            return METADATA [typeID];
-        }
-        
-        public static IItemMetadata [] getAllTypes ()
-        {
-            return METADATA;
-        }
-        
-        private Factory () {}
-        
-        
-        private static final IItemMetadata [] METADATA; // set in <clinit>
-        
-        static
-        {
-            // this establishes the mapping TYPE_ID_xxx->metadata for type xxx:
-            
-            METADATA = new IItemMetadata []
-            {
-                AllItem.getTypeMetadata (),
-                PackageItem.getTypeMetadata (),
-                SrcFileItem.getTypeMetadata (),
-                ClassItem.getTypeMetadata (),
-                MethodItem.getTypeMetadata (),
-            };
-        }
-        
-    } // end of nested class 
-    
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/IItemVisitor.java b/core/java12/com/vladium/emma/report/IItemVisitor.java
deleted file mode 100644
index eec3333..0000000
--- a/core/java12/com/vladium/emma/report/IItemVisitor.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IItemVisitor.java,v 1.1.1.1 2004/05/09 16:57:37 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public interface IItemVisitor
-{
-    // public: ................................................................
-    
-    Object visit (AllItem item, Object ctx);
-    Object visit (PackageItem item, Object ctx);
-    Object visit (SrcFileItem item, Object ctx);
-    Object visit (ClassItem item, Object ctx);
-    Object visit (MethodItem item, Object ctx);
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/IReportDataModel.java b/core/java12/com/vladium/emma/report/IReportDataModel.java
deleted file mode 100644
index 9b0b8b3..0000000
--- a/core/java12/com/vladium/emma/report/IReportDataModel.java
+++ /dev/null
@@ -1,39 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IReportDataModel.java,v 1.1.1.1 2004/05/09 16:57:37 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import com.vladium.emma.data.ICoverageData;
-import com.vladium.emma.data.IMetaData;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IReportDataModel
-{
-    // public: ................................................................
-    
-    IReportDataView getView (int viewType);
-    
-    abstract class Factory
-    {
-        /**
-         * This operation merely stores mdata and cdata references, it does not
-         * perform any data processing until getView() is actually called.
-         */
-        public static IReportDataModel create (final IMetaData mdata, final ICoverageData cdata)
-        {
-            return new ReportDataModel (mdata, cdata);
-        }
-        
-    } // end of nested class
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/IReportDataView.java b/core/java12/com/vladium/emma/report/IReportDataView.java
deleted file mode 100644
index 4b32bfe..0000000
--- a/core/java12/com/vladium/emma/report/IReportDataView.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IReportDataView.java,v 1.1.1.1 2004/05/09 16:57:37 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public interface IReportDataView
-{
-    // public: ................................................................
-    
-
-    int HIER_CLS_VIEW   = 0;
-    int HIER_SRC_VIEW   = 1;   
-    
-    IItem getRoot ();
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/IReportGenerator.java b/core/java12/com/vladium/emma/report/IReportGenerator.java
deleted file mode 100644
index 4dc2a3c..0000000
--- a/core/java12/com/vladium/emma/report/IReportGenerator.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IReportGenerator.java,v 1.1.1.1 2004/05/09 16:57:37 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import com.vladium.util.IProperties;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.data.IMetaData;
-import com.vladium.emma.data.ICoverageData;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IReportGenerator
-{
-    // public: ................................................................
-    
-    String getType ();
-    
-    // TODO: make sure reporters are reusable
-    
-    void process (IMetaData mdata, ICoverageData cdata, SourcePathCache cache, IProperties parameters)
-        throws EMMARuntimeException;
-    
-    void cleanup ();
-        
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/IReportProperties.java b/core/java12/com/vladium/emma/report/IReportProperties.java
deleted file mode 100644
index 6d5f963..0000000
--- a/core/java12/com/vladium/emma/report/IReportProperties.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IReportProperties.java,v 1.1.1.1 2004/05/09 16:57:37 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IReportProperties
-{
-    // public: ................................................................
-   
-    // TODO: separate props for diff kinds of files (m, c, reports) ?
-    
-    String PREFIX = "report.";
-    
-    // parameter:
-    String OUT_ENCODING     = "out.encoding";
-    String OUT_DIR          = "out.dir";
-    String OUT_FILE         = "out.file";
-
-    // parameter:
-    String UNITS_TYPE       = "units";
-    // values:
-    String COUNT_UNITS      = "count";
-    String INSTR_UNITS      = "instr";
-        
-    // parameter:
-    String VIEW_TYPE        = "view";
-    // values:
-    String CLS_VIEW         = "class";
-    String SRC_VIEW         = "source";
-
-    // parameter:
-    String HIDE_CLASSES     = "hideclasses"; // boolean
-    
-    // parameter:
-    String DEPTH            = "depth";
-    // values:
-    String DEPTH_ALL        = "all";
-    String DEPTH_PACKAGE    = "package";
-    String DEPTH_SRCFILE    = "source";
-    String DEPTH_CLASS      = "class";
-    String DEPTH_METHOD     = "method";
-    
-    // parameter:
-    String COLUMNS          = "columns"; // comma-separated list
-    // values:
-    String ITEM_NAME_COLUMN         = "name";
-    String CLASS_COVERAGE_COLUMN    = "class";
-    String METHOD_COVERAGE_COLUMN   = "method";
-    String BLOCK_COVERAGE_COLUMN    = "block";
-    String LINE_COVERAGE_COLUMN     = "line";
-    
-    // parameter:
-    String SORT             = "sort"; // comma-separated list of ('+'/'-'-prefixed column names)
-    char ASC                = '+'; // default
-    char DESC               = '-';
-    
-    // parameter:
-    String METRICS          = "metrics"; // comma-separated list of (column name:metric) pairs
-    char MSEPARATOR         = ':';
-
-    // defaults:
-    
-    String DEFAULT_UNITS_TYPE = INSTR_UNITS;
-    String DEFAULT_VIEW_TYPE = SRC_VIEW;
-    String DEFAULT_HIDE_CLASSES = "true";
-    String DEFAULT_DEPTH = DEPTH_PACKAGE;
-    String DEFAULT_COLUMNS = CLASS_COVERAGE_COLUMN + "," + METHOD_COVERAGE_COLUMN + "," + BLOCK_COVERAGE_COLUMN + "," + LINE_COVERAGE_COLUMN + "," + ITEM_NAME_COLUMN;
-    String DEFAULT_SORT = ASC + BLOCK_COVERAGE_COLUMN + "," + ASC + ITEM_NAME_COLUMN;
-    String DEFAULT_METRICS = METHOD_COVERAGE_COLUMN + MSEPARATOR + "70," + BLOCK_COVERAGE_COLUMN + MSEPARATOR + "80," + LINE_COVERAGE_COLUMN + MSEPARATOR + "80," + CLASS_COVERAGE_COLUMN + MSEPARATOR + "100";
-
-} // end of inteface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/Item.java b/core/java12/com/vladium/emma/report/Item.java
deleted file mode 100644
index 182a24a..0000000
--- a/core/java12/com/vladium/emma/report/Item.java
+++ /dev/null
@@ -1,162 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Item.java,v 1.1.1.1.2.1 2004/06/20 20:14:39 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Iterator;
-import java.util.List;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-abstract class Item implements IItem
-{
-    // public: ................................................................
-
-    
-    // IItem:
-    
-    public final int getChildCount ()
-    {
-        return m_children.size ();
-    }
-
-    public final IItem getParent ()
-    {
-        return m_parent;
-    }
-
-    public final Iterator getChildren ()
-    {
-        return m_children.iterator ();
-    }
-    
-    public final Iterator getChildren (final ItemComparator /* IItem */ order)
-    {
-        // TODO: soft caching keyed off 'order'
-        
-        if (order == null)
-            return getChildren ();
-        else
-        {        
-            final IItem [] items = new IItem [m_children.size ()];
-            m_children.toArray (items);
-            
-            Arrays.sort (items, order);
-            
-            return Arrays.asList (items).iterator ();
-        }
-    }
-    
-    public final IItemAttribute getAttribute (final int attributeID, final int unitsID)
-    {
-        //if ($assert.ENABLED) $assert.ASSERT ((attributeID & getMetadata ().getAttributeIDs ()) != 0, "invalid attribute ID [" + attributeID + "] for type [" + getMetadata ().getTypeID () + "]");
-        
-        if ((getMetadata ().getAttributeIDs () & (1 << attributeID)) == 0)
-            return null;
-        else
-            return IItemAttribute.Factory.getAttribute (attributeID, unitsID);
-    }
-    
-    public int getAggregate (final int type)
-    {
-        final int [] aggregates = m_aggregates;
-        int value = aggregates [type];
-        
-        if (value < 0)
-        {
-            // don't fault aggregate types all at once since there are
-            // plenty of exceptions to the additive roll up rule:
-            
-            value = 0;
-            for (Iterator children = m_children.iterator (); children.hasNext (); )
-            {
-                value += ((IItem) children.next ()).getAggregate (type);
-            }
-            aggregates [type] = value;
-            
-            return value;
-        }
-        
-        return value;
-    }
-
-    // protected: .............................................................
-    
-    
-    protected static final class ItemMetadata implements IItemMetadata
-    {
-        public int getTypeID ()
-        {
-            return m_typeID;
-        }
-        
-        public String getTypeName ()
-        {
-            return m_typeName;
-        }
-        
-        public long getAttributeIDs ()
-        {
-            return m_attributeIDs;
-        }
-        
-        ItemMetadata (final int typeID, final String typeName, final long attributeIDs)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (typeID >= TYPE_ID_ALL && typeID <= TYPE_ID_METHOD, "invalid type ID: " + typeID);
-            if ($assert.ENABLED) $assert.ASSERT (typeName != null, "typeName = null");
-            
-            
-            m_typeID = typeID;
-            m_typeName = typeName;
-            m_attributeIDs = attributeIDs;
-        }
-
-
-        private final int m_typeID;
-        private final String m_typeName;
-        private final long m_attributeIDs;
-        
-    } // end of nested class
-
-
-    protected void addChild (final IItem item)
-    {
-        if (item == null) throw new IllegalArgumentException ("null input: item");
-        
-        m_children.add (item);
-    }
-    
-    
-    protected final IItem m_parent;
-    protected final int [] m_aggregates;
-
-    // package: ...............................................................
-    
-
-    Item (final IItem parent)
-    {
-        m_parent = parent;
-        m_children = new ArrayList ();
-        
-        m_aggregates = new int [NUM_OF_AGGREGATES];
-        for (int i = 0; i < m_aggregates.length; ++ i) m_aggregates [i] = -1;
-    }
-    
-    // private: ...............................................................
-    
-    
-    private final List m_children;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/ItemComparator.java b/core/java12/com/vladium/emma/report/ItemComparator.java
deleted file mode 100644
index ff33b1b..0000000
--- a/core/java12/com/vladium/emma/report/ItemComparator.java
+++ /dev/null
@@ -1,110 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ItemComparator.java,v 1.1.1.1 2004/05/09 16:57:37 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.util.Comparator;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface ItemComparator extends Comparator
-{
-    // public: ................................................................
-    
-    
-    ItemComparator NULL_COMPARATOR = new Factory.NullComparator ();
-    
-    
-    abstract class Factory
-    {
-        public static ItemComparator create (final int [] attributeIDsWithDir, final int unitsID)
-        {
-            if (attributeIDsWithDir == null)
-                throw new IllegalArgumentException ("null input: attributeIDsWithDir");
-            
-            if (attributeIDsWithDir.length == 0)
-                return NULL_COMPARATOR;
-                
-            // TODO: validate against duplicates
-            // TODO: memoize
-            
-            // TODO: move the code below into the attr factory
-            final Comparator [] comparators = new Comparator [attributeIDsWithDir.length >> 1];
-            for (int a = 0; a < attributeIDsWithDir.length; a += 2)
-            {
-                final int attributeID = attributeIDsWithDir [a];
-                
-                final Comparator comparator = IItemAttribute.Factory.getAttribute (attributeID, unitsID).comparator ();
-                comparators [a >> 1] = attributeIDsWithDir [a + 1] < 0 ? new ReverseComparator (comparator) : comparator;
-            }
-            
-            return new CompositeComparator (comparators);
-        }
-
-        private static final class NullComparator implements ItemComparator
-        {
-            public int compare (final Object l, final Object g)
-            {
-                return 0; 
-            }
-            
-        } // end of nested class
-        
-        
-        private static final class ReverseComparator implements ItemComparator
-        {
-            public int compare (final Object l, final Object g)
-            {
-                return m_comparator.compare (g, l); 
-            }
-
-            
-            ReverseComparator (final Comparator comparator)
-            {
-                m_comparator = comparator;
-            }
-            
-            
-            private final Comparator m_comparator;
-            
-        } // end of nested class
-        
-        
-        private static final class CompositeComparator implements ItemComparator
-        {
-            public int compare (final Object l, final Object g)
-            {
-                // TODO: this needs to check whether both items have a given attr type
-                
-                for (int c = 0; c < m_comparators.length; ++ c)
-                {
-                    final int diff = m_comparators [c].compare (l, g);
-                    if (diff != 0) return diff;
-                }
-                
-                return 0;
-            }
-
-            
-            CompositeComparator (final Comparator [] comparators)
-            {
-                m_comparators = comparators;
-            }
-            
-            
-            private final Comparator [] m_comparators;
-            
-        } // end of nested class
-        
-    } // end of nested interface 
-    
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/MethodItem.java b/core/java12/com/vladium/emma/report/MethodItem.java
deleted file mode 100644
index 0627b74..0000000
--- a/core/java12/com/vladium/emma/report/MethodItem.java
+++ /dev/null
@@ -1,218 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: MethodItem.java,v 1.1.1.1.2.1 2004/06/20 20:07:22 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import com.vladium.util.Descriptors;
-import com.vladium.util.IntObjectMap;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.data.IMetadataConstants;
-import com.vladium.emma.data.MethodDescriptor;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class MethodItem extends Item
-{
-    // public: ................................................................
-    
-    public MethodItem (final IItem parent, final int ID, final String name, final String descriptor, final int firstLine)
-    {
-        super (parent);
-        
-        m_ID = ID;
-        m_name = name;
-        m_descriptor = descriptor;
-        m_firstLine = firstLine;
-    }
-      
-    public String getName ()
-    {
-        if (m_userName == null)
-        {
-            m_userName = Descriptors.methodVMNameToJavaName (m_parent.getName (), m_name, m_descriptor, true, true, true);
-        }
-        
-        return m_userName;
-    }
-    
-    public int getID ()
-    {
-        return m_ID;
-    }
-    
-    public int getFirstLine ()
-    {
-        return m_firstLine;
-    }
-    
-    public int getAggregate (final int type)
-    {
-        final int [] aggregates = m_aggregates;
-        
-        int value = aggregates [type];
-        
-        if (value < 0)
-        {
-            final ClassItem parent = ((ClassItem) m_parent);
-            
-            final MethodDescriptor method = parent.m_cls.getMethods () [m_ID];
-            final int status = method.getStatus ();
-                    
-            if ((status & IMetadataConstants.METHOD_NO_BLOCK_DATA) != 0)
-            {
-                if ($assert.ENABLED) $assert.ASSERT (false, "excluded method in report data model");
-                
-                for (int i = 0; i < aggregates.length; ++ i) aggregates [i] = 0;
-            }
-            else
-            {
-                final boolean lineInfo = ((status & IMetadataConstants.METHOD_NO_LINE_NUMBER_TABLE) == 0);                
-                final boolean [] coverage = parent.m_coverage != null ? parent.m_coverage [m_ID] : null;  
-                              
-                final int totalBlockCount = method.getBlockCount ();
-
-                aggregates [TOTAL_METHOD_COUNT] = 1; // TODO: check that excluded methods are accounted for correctly                
-                aggregates [TOTAL_BLOCK_COUNT] = totalBlockCount;
-                                
-                int totalBlockInstr = 0;
-                
-                final int [] blockSizes = method.getBlockSizes ();
-                
-                if (coverage != null)
-                {
-                    int coverageBlockCount = 0, coverageLineCount = 0;
-                    int coverageBlockInstr = 0, coverageLineInstr = 0;
-
-                    for (int b = 0; b < totalBlockCount; ++ b)
-                    {
-                        final int instr = blockSizes [b];
-                         
-                        totalBlockInstr += instr;
-                        if (coverage [b])
-                        {
-                            ++ coverageBlockCount;
-                            coverageBlockInstr += instr;
-                        }
-                    }
-                    
-                    if (lineInfo)
-                    {
-                        final IntObjectMap lineMap = method.getLineMap (); // TODO: expensive way to get totalLineCount
-                        final int totalLineCount = lineMap.size ();
-                    
-                        aggregates [TOTAL_LINE_COUNT] = totalLineCount;
-                        
-                        final int [] lines = lineMap.keys ();
-                        for (int l = 0; l < totalLineCount; ++ l)
-                        {
-                            final int [] blocks = (int []) lineMap.get (lines [l]);
-                            
-                            int thisLineCoverageCount = 0; final int thisLineTotalCount = blocks.length;
-                            int thisLineCoverageInstr = 0, thisLineTotalInstr = 0;
-                            
-                            for (int bID = 0; bID < thisLineTotalCount; ++ bID)
-                            {
-                                final int b = blocks [bID];
-
-                                final int instr = blockSizes [b];
-                                
-                                thisLineTotalInstr += instr;
-                                if (coverage [b])
-                                {
-                                    ++ thisLineCoverageCount;
-                                    thisLineCoverageInstr += instr;
-                                }
-                            }
-                            
-                            coverageLineCount += (PRECISION * thisLineCoverageCount) / thisLineTotalCount;
-                            coverageLineInstr += (PRECISION * thisLineCoverageInstr) / thisLineTotalInstr;
-                        }
-                        
-                        aggregates [COVERAGE_LINE_COUNT] = coverageLineCount;
-                        aggregates [COVERAGE_LINE_INSTR] = coverageLineInstr;
-                    }
-
-                    aggregates [TOTAL_BLOCK_INSTR] = totalBlockInstr;
-                    aggregates [COVERAGE_METHOD_COUNT] = coverageBlockCount > 0 ? 1 : 0;                                        
-                    aggregates [COVERAGE_BLOCK_COUNT] = coverageBlockCount;
-                    aggregates [COVERAGE_BLOCK_INSTR] = coverageBlockInstr;
-                    
-                }
-                else
-                {
-                    for (int b = 0; b < totalBlockCount; ++ b)
-                    {
-                        totalBlockInstr += blockSizes [b];
-                    }
-                        
-                    aggregates [TOTAL_BLOCK_INSTR] = totalBlockInstr;
-                    aggregates [COVERAGE_METHOD_COUNT] = 0;
-                    aggregates [COVERAGE_BLOCK_COUNT] = 0;
-                    aggregates [COVERAGE_BLOCK_INSTR] = 0;
-                    
-                    if (lineInfo)
-                    {
-                        final IntObjectMap lineMap = method.getLineMap (); // TODO: expensive way to get totalLineCount
-                        final int totalLineCount = lineMap.size ();
-                    
-                        aggregates [TOTAL_LINE_COUNT] = totalLineCount;    
-                        aggregates [COVERAGE_LINE_COUNT] = 0;
-                        aggregates [COVERAGE_LINE_INSTR] = 0;
-                    }
-                }
-            }
-            
-            return aggregates [type];
-        }
-        
-        return value;
-    }
-       
-    public void accept (final IItemVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-
-    public final IItemMetadata getMetadata ()
-    {
-        return METADATA;
-    }
-    
-    public static IItemMetadata getTypeMetadata ()
-    {
-        return METADATA;
-    }
-        
-    // protected: .............................................................
-
-    // package: ...............................................................
-        
-    // private: ...............................................................
-    
-    
-    private final int m_ID;
-    private final String m_name, m_descriptor;
-    private final int m_firstLine;
-    private transient String m_userName;
-    
-    private static final Item.ItemMetadata METADATA; // set in <clinit>
-        
-    static
-    {
-        METADATA = new Item.ItemMetadata (IItemMetadata.TYPE_ID_METHOD, "method",
-            1 << IItemAttribute.ATTRIBUTE_NAME_ID |
-            1 << IItemAttribute.ATTRIBUTE_METHOD_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_BLOCK_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_LINE_COVERAGE_ID);
-    }
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/PackageItem.java b/core/java12/com/vladium/emma/report/PackageItem.java
deleted file mode 100644
index f6c7049..0000000
--- a/core/java12/com/vladium/emma/report/PackageItem.java
+++ /dev/null
@@ -1,76 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: PackageItem.java,v 1.1.1.1 2004/05/09 16:57:38 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class PackageItem extends Item
-{
-    // public: ................................................................
-    
-    public PackageItem (final IItem parent, final String name, final String VMname) // TODO: this is VM name for now
-    {
-        super (parent);
-        
-        m_name = name;
-        m_VMname = VMname;
-    }
-    
-    public String getName ()
-    {
-        return m_name;
-    }
-    
-    public String getVMName ()
-    {
-        return m_VMname;
-    }
-    
-    public void accept (final IItemVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public final IItemMetadata getMetadata ()
-    {
-        return METADATA;
-    }
-    
-    public static IItemMetadata getTypeMetadata ()
-    {
-        return METADATA;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private final String m_name, m_VMname;
-    
-    private static final Item.ItemMetadata METADATA; // set in <clinit>
-        
-    static
-    {
-        METADATA = new Item.ItemMetadata (IItemMetadata.TYPE_ID_PACKAGE, "package",
-            1 << IItemAttribute.ATTRIBUTE_NAME_ID |
-            1 << IItemAttribute.ATTRIBUTE_CLASS_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_METHOD_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_BLOCK_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_LINE_COVERAGE_ID);
-    }
-
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/ReportDataModel.java b/core/java12/com/vladium/emma/report/ReportDataModel.java
deleted file mode 100644
index 4f94d75..0000000
--- a/core/java12/com/vladium/emma/report/ReportDataModel.java
+++ /dev/null
@@ -1,179 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ReportDataModel.java,v 1.1.1.1 2004/05/09 16:57:38 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Map;
-
-import com.vladium.util.Descriptors;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.data.ClassDescriptor;
-import com.vladium.emma.data.IMetaData;
-import com.vladium.emma.data.IMetadataConstants;
-import com.vladium.emma.data.ICoverageData;
-import com.vladium.emma.data.MethodDescriptor;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-final class ReportDataModel implements IReportDataModel
-{
-    // public: ................................................................
-
-
-    public synchronized IReportDataView getView (final int viewType)
-    {
-        // TODO: merge the two branches together
-        
-        if (viewType >= m_views.length) throw new IllegalArgumentException ("invalid viewType: " + viewType);
-        
-        IReportDataView view = m_views [viewType];
-        
-        if (view != null)
-            return view;
-        else
-        {
-            final boolean srcView = viewType == IReportDataView.HIER_SRC_VIEW;
-            
-            if (srcView && ! m_mdata.hasSrcFileData ())
-                throw new IllegalStateException ("source file data view requested for metadata with incomplete SourceFile debug info");
-
-            final AllItem root = new AllItem ();
-            final Map /* String(pkg name) -> PackageItem */ packageMap = new HashMap ();
-            final Map /* String(pkg-prefixed src file name) -> ClassItem */ srcfileMap = new HashMap ();
-            
-            for (Iterator /* ClassDescriptor */ descriptors = m_mdata.iterator (); descriptors.hasNext (); )
-            {    
-                final ClassDescriptor cls = (ClassDescriptor) descriptors.next ();
-                String packageVMName = cls.getPackageVMName ();
-                
-                PackageItem packageItem = (PackageItem) packageMap.get (packageVMName);
-                if (packageItem == null)
-                {
-                    final String packageName = packageVMName.length () == 0 ? "default package" : Descriptors.vmNameToJavaName (packageVMName); 
-                    packageItem = new PackageItem (root, packageName, packageVMName);
-                    packageMap.put (packageVMName, packageItem);
-                    
-                    root.addChild (packageItem);
-                }
-                
-                SrcFileItem srcfileItem = null;
-                if (srcView)
-                {                
-                    final String srcFileName = cls.getSrcFileName ();
-                    if ($assert.ENABLED) $assert.ASSERT (srcFileName != null, "src file name = null");
-                    
-                    final String fullSrcFileName = Descriptors.combineVMName (packageVMName, srcFileName);
-                    
-                    srcfileItem = (SrcFileItem) srcfileMap.get (fullSrcFileName);
-                    if (srcfileItem == null)
-                    {
-                        srcfileItem = new SrcFileItem (packageItem, srcFileName, fullSrcFileName);
-                        srcfileMap.put (fullSrcFileName, srcfileItem);
-                        
-                        packageItem.addChild (srcfileItem);
-                    }
-                }
-                
-                final ICoverageData.DataHolder data = m_cdata.getCoverage (cls);
-                
-                // check metadata and coverage data consistency:
-                
-                if (data != null)
-                {
-                    if (data.m_stamp != cls.getStamp ())
-                        throw new EMMARuntimeException (IAppErrorCodes.CLASS_STAMP_MISMATCH,
-                                                        new Object [] { Descriptors.vmNameToJavaName (cls.getClassVMName ()) }); 
-                }
-                
-                final boolean [][] coverage = data != null ? data.m_coverage : null;
-                
-                if ($assert.ENABLED) $assert.ASSERT (! srcView || srcfileItem != null, "null srcfileItem");
-                
-                final ClassItem classItem = srcView ? new ClassItem (srcfileItem, cls, coverage) : new ClassItem (packageItem, cls, coverage);
-                final MethodDescriptor [] methods = cls.getMethods ();
-                
-                // TODO: handle edge case when all methods of a class have METHOD_NO_BLOCK_DATA set
-                for (int m = 0; m < methods.length; ++ m)
-                {
-                    final MethodDescriptor method = methods [m];
-                        
-                    if ((method.getStatus () & IMetadataConstants.METHOD_NO_BLOCK_DATA) != 0) continue;
-                    
-                    // TODO: wouldn't it be more consistent to simply pass the entire descriptor into MethodItems? (eval mem savings)
-                    final MethodItem methodItem = new MethodItem (classItem, m, method.getName (), method.getDescriptor (), method.getFirstLine ());                    
-                    // TODO: need to fold class's name into a method name prefix for collapsing case [only when it is not the same as the file name]
-                    
-                    classItem.addChild (methodItem);
-                }
-                
-                if (srcView)
-                    srcfileItem.addChild (classItem);
-                else
-                    packageItem.addChild (classItem);
-            }
-            
-            view = new ReportDataView (root);
-            
-            m_views [viewType] = view;
-            return view;
-        }
-    }
-
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    
-    ReportDataModel (final IMetaData mdata, final ICoverageData cdata)
-    {
-        if (mdata == null) throw new IllegalArgumentException ("null input: mdata");
-        if (cdata == null) throw new IllegalArgumentException ("null input: cdata");
-        
-        m_views = new IReportDataView [2];
-        
-        // TODO: report generators work off data model views only; I should deref
-        // mdata and cdata as soon as all possible views have been constructed and cached
-        
-        m_mdata = mdata;
-        m_cdata = cdata;
-    }
-    
-    // private: ...............................................................
-    
-    
-    private static final class ReportDataView implements IReportDataView
-    {
-        public IItem getRoot()
-        {
-            return m_root;
-        }
-        
-        ReportDataView (final IItem root)
-        {
-            m_root = root;
-        }
-        
-        
-        private final IItem m_root;
-        
-    } // end of nested class
-    
-    
-    private final IMetaData m_mdata;
-    private final ICoverageData m_cdata;
-    
-    private final IReportDataView [] m_views;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/ReportProcessor.java b/core/java12/com/vladium/emma/report/ReportProcessor.java
deleted file mode 100644
index 04fb09a..0000000
--- a/core/java12/com/vladium/emma/report/ReportProcessor.java
+++ /dev/null
@@ -1,341 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ReportProcessor.java,v 1.1.1.1.2.2 2004/07/16 23:32:29 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.io.File;
-import java.io.IOException;
-
-import com.vladium.logging.Logger;
-import com.vladium.util.Files;
-import com.vladium.util.IConstants;
-import com.vladium.util.IProperties;
-import com.vladium.util.Strings;
-import com.vladium.util.asserts.$assert;
-import com.vladium.util.exception.Exceptions;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.Processor;
-import com.vladium.emma.data.DataFactory;
-import com.vladium.emma.data.ICoverageData;
-import com.vladium.emma.data.IMergeable;
-import com.vladium.emma.data.IMetaData;
-
-// ----------------------------------------------------------------------------
-/*
- * This class was not meant to be public by design. It is made to to work around
- * access bugs in reflective invocations. 
- */
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class ReportProcessor extends Processor
-                            implements IAppErrorCodes
-{
-    // public: ................................................................
-    
-    public static ReportProcessor create ()
-    {
-        return new ReportProcessor ();
-    }
-    
-    /**
-     * 
-     * @param path [null is equivalent to an empty array]
-     */
-    public synchronized final void setDataPath (final String [] path)
-    {
-        if ((path == null) || (path.length == 0))
-            m_dataPath = IConstants.EMPTY_FILE_ARRAY;
-        else
-            m_dataPath = Files.pathToFiles (path, true);
-    }
-    
-    /**
-     * @param path [null is equivalent to no source path]
-     */
-    public synchronized void setSourcePath (final String [] path)
-    {
-        if (path == null)
-            m_sourcePath = null;
-        else
-            m_sourcePath = Files.pathToFiles (path, true); // always canonicalize source path
-    }
-
-    /**
-     * 
-     * @param types [may not be null]
-     */
-    public synchronized void setReportTypes (final String [] types)
-    {
-        if (types == null) throw new IllegalArgumentException ("null input: types");
-        
-        final String [] reportTypes = Strings.removeDuplicates (types, true);
-        if (reportTypes.length == 0) throw new IllegalArgumentException ("empty input: types");
-        
-        if ($assert.ENABLED) $assert.ASSERT (reportTypes != null && reportTypes.length  > 0);
-        
-        
-        final IReportGenerator [] reportGenerators = new IReportGenerator [reportTypes.length];
-        for (int t = 0; t < reportTypes.length; ++ t)
-        {
-            reportGenerators [t] = AbstractReportGenerator.create (reportTypes [t]);
-        }
-        
-        m_reportGenerators = reportGenerators;
-    }
-    
-    // protected: .............................................................
-
-    
-    protected void validateState ()
-    {
-        super.validateState ();
-        
-        if (m_dataPath == null)
-            throw new IllegalStateException ("data path not set");
-            
-        // [m_sourcePath can be null]
-        
-        if ((m_reportGenerators == null) || (m_reportGenerators.length == 0))
-            throw new IllegalStateException ("report types not set");
-        
-        // [m_propertyOverrides can be null]
-    }
-
-    
-    protected void _run (final IProperties toolProperties)
-    {
-        final Logger log = m_log;
-        
-        final boolean verbose = m_log.atVERBOSE ();
-        if (verbose)
-        {
-            log.verbose (IAppConstants.APP_VERBOSE_BUILD_ID);
-            
-            // [assertion: m_dataPath != null]
-            log.verbose ("input data path:");
-            log.verbose ("{");
-            for (int p = 0; p < m_dataPath.length; ++ p)
-            {
-                final File f = m_dataPath [p];
-                final String nonexistent = f.exists () ? "" : "{nonexistent} ";
-                
-                log.verbose ("  " + nonexistent + f.getAbsolutePath ());
-            }
-            log.verbose ("}");
-            
-            
-            if ((m_sourcePath == null) || (m_sourcePath.length == 0))
-            {
-                log.verbose ("source path not set");
-            }
-            else
-            {
-                log.verbose ("source path:");
-                log.verbose ("{");
-                for (int p = 0; p < m_sourcePath.length; ++ p)
-                {
-                    final File f = m_sourcePath [p];
-                    final String nonexistent = f.exists () ? "" : "{nonexistent} ";
-                    
-                    log.verbose ("  " + nonexistent + f.getAbsolutePath ());
-                }
-                log.verbose ("}");
-            }
-        }
-        else
-        {
-            log.info ("processing input files ...");
-        }
-        
-        RuntimeException failure = null;
-        try
-        {
-            final long start = log.atINFO () ? System.currentTimeMillis () : 0;
-            
-            IMetaData mdata = null;
-            ICoverageData cdata = null;
-            
-            // merge all data files:
-            try
-            {
-                for (int f = 0; f < m_dataPath.length; ++ f)
-                {
-                    final File dataFile = m_dataPath [f];
-                    if (verbose) log.verbose ("processing input file [" + dataFile.getAbsolutePath () + "] ...");
-                    
-                    final IMergeable [] fileData = DataFactory.load (dataFile);
-                    
-                    final IMetaData _mdata = (IMetaData) fileData [DataFactory.TYPE_METADATA];
-                    if (_mdata != null)
-                    {
-                        if (verbose) log.verbose ("  loaded " + _mdata.size () + " metadata entries");
-                        
-                        if (mdata == null)
-                            mdata = _mdata;
-                        else
-                            mdata = (IMetaData) mdata.merge (_mdata); // note: later datapath entries override earlier ones
-                    }
-                    
-                    final ICoverageData _cdata = (ICoverageData) fileData [DataFactory.TYPE_COVERAGEDATA];
-                    if (_cdata != null)
-                    {
-                        if (verbose) log.verbose ("  loaded " + _cdata.size () + " coverage data entries");
-                        
-                        if (cdata == null)
-                            cdata = _cdata;
-                        else
-                            cdata = (ICoverageData) cdata.merge (_cdata); // note: later datapath entries override earlier ones
-                    }
-                    
-                    ++ m_dataFileCount;
-                }
-                
-                if (log.atINFO ())
-                {
-                    final long end = System.currentTimeMillis ();
-                    
-                    log.info (m_dataFileCount + " file(s) read and merged in " + (end - start) + " ms");
-                }
-                
-                if ((mdata == null) || mdata.isEmpty ())
-                {
-                    log.warning ("nothing to do: no metadata found in any of the data files");
-                    
-                    return;
-                }
-                
-                if (cdata == null)
-                {
-                    log.warning ("nothing to do: no runtime coverage data found in any of the data files");
-                    
-                    return;
-                }
-                
-                if (cdata.isEmpty ())
-                {
-                    log.warning ("no collected coverage data found in any of the data files [all reports will be empty]");
-                }
-                
-                
-                if (verbose)
-                {
-                    if (mdata != null)
-                    {
-                        log.verbose ("  merged metadata contains " + mdata.size () + " entries");
-                    }
-                    
-                    if (cdata != null)
-                    {
-                        log.verbose ("  merged coverage data contains " + cdata.size () + " entries");
-                    }
-                }
-                                
-                SourcePathCache srcpathCache = null;
-                if (m_sourcePath != null) srcpathCache = new SourcePathCache (m_sourcePath, true); // ignore non-existent source dirs 
-                
-                for (int g = 0; g < m_reportGenerators.length; ++ g)
-                {
-                    final IReportGenerator generator = m_reportGenerators [g];
-                    
-                    try
-                    {
-                        // no shallow copies of 'mdata' or 'cdata' are needed here
-                        // because this command never runs in a concurrent situation
-                        
-                        generator.process (mdata, cdata, srcpathCache, toolProperties);
-                    }
-                    catch (Throwable t)
-                    {
-                        // TODO: handle and continue
-                        t.printStackTrace (System.out);
-                        
-                        // TODO: continue here
-                        break;
-                    }
-                    finally
-                    {
-                        try { generator.cleanup (); } catch (Throwable ignore) {}
-                    }
-                }
-            }
-            catch (IOException ioe)
-            {
-                // TODO: handle
-                ioe.printStackTrace (System.out);
-            }
-        }
-        catch (SecurityException se)
-        {
-            failure = new EMMARuntimeException (SECURITY_RESTRICTION, new String [] {IAppConstants.APP_NAME}, se);
-        }
-        catch (RuntimeException re)
-        {
-            failure = re;
-        }
-        finally
-        {
-            reset ();
-        }
-        
-        if (failure != null)
-        {
-            if (Exceptions.unexpectedFailure (failure, EXPECTED_FAILURES))
-            {
-                throw new EMMARuntimeException (UNEXPECTED_FAILURE,
-                                                new Object [] {failure.toString (), IAppConstants.APP_BUG_REPORT_LINK},
-                                                failure);
-            }
-            else
-                throw failure;
-        }
-    }
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private ReportProcessor ()
-    {
-        m_dataPath = IConstants.EMPTY_FILE_ARRAY;
-    }
-    
-    private void reset ()
-    {
-        m_dataFileCount = 0;
-    }
-    
-    
-    // caller-settable state [scoped to this runner instance]:
-    
-    private File [] m_dataPath;     // required to be non-null for run()
-    private File [] m_sourcePath;   // can be null/empty for run()
-    private IReportGenerator [] m_reportGenerators; // required to be non-null for run()
-
-    // internal run()-scoped state:
-    
-    private int m_dataFileCount;    
-    
-    private static final Class [] EXPECTED_FAILURES; // set in <clinit>
-    
-    static
-    {
-        EXPECTED_FAILURES = new Class []
-        {
-            EMMARuntimeException.class,
-            IllegalArgumentException.class,
-            IllegalStateException.class,
-        };
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/ReportProperties.java b/core/java12/com/vladium/emma/report/ReportProperties.java
deleted file mode 100644
index 940ca36..0000000
--- a/core/java12/com/vladium/emma/report/ReportProperties.java
+++ /dev/null
@@ -1,576 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ReportProperties.java,v 1.1.1.1 2004/05/09 16:57:38 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.io.File;
-import java.util.HashSet;
-import java.util.Set;
-import java.util.StringTokenizer;
-
-import com.vladium.util.Files;
-import com.vladium.util.IProperties;
-import com.vladium.util.IntIntMap;
-import com.vladium.util.IntVector;
-import com.vladium.util.ObjectIntMap;
-import com.vladium.util.Property;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMARuntimeException;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class ReportProperties implements IAppErrorCodes
-{
-    // public: ................................................................
-    
-    
-    public static final IProperties.IMapper REPORT_PROPERTY_MAPPER; // set in <clinit>
-    
-       
-    public static final class ParsedProperties
-    {
-        public void setOutEncoding (final String outEncoding)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (outEncoding != null, "null input: outEncoding");
-            
-            m_outEncoding = outEncoding;
-        }
-
-        public String getOutEncoding ()
-        {
-            return m_outEncoding;
-        }
-
-        public void setOutDir (final File outDir)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (outDir != null, "null input: outDir");
-            
-            m_outDir = outDir;
-        }
-
-        public File getOutDir ()
-        {
-            return m_outDir;
-        }
-
-        public void setOutFile (final File outFile)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (outFile != null, "null input: outFile");
-            
-            m_outFile = outFile;
-        }
-
-        public File getOutFile ()
-        {
-            return m_outFile;
-        }
-
-        public void setUnitsType (final int unitsType)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (unitsType >= IItemAttribute.UNITS_COUNT && unitsType <= IItemAttribute.UNITS_INSTR, "invalid units type: " + unitsType);
-            
-            m_unitsType = unitsType;
-        }
-
-        public int getUnitsType ()
-        {
-            return m_unitsType;
-        }
-
-        public void setViewType (final int viewType)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (viewType >= IReportDataView.HIER_CLS_VIEW && viewType <= IReportDataView.HIER_SRC_VIEW, "invalid view type: " + viewType);
-            
-            m_viewType = viewType;
-        }
-
-        public int getViewType ()
-        {
-            return m_viewType;
-        }
-
-        public void setDepth (final int depth)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (depth >= IItemMetadata.TYPE_ID_ALL && depth <= IItemMetadata.TYPE_ID_METHOD, "invalid depth: " + depth);
-            
-            m_depth = depth;
-        }
-
-        public int getDepth()
-        {
-            return m_depth;
-        }
-
-        public void setHideClasses (final boolean hideClasses)
-        {
-            m_hideClasses = hideClasses;
-        }
-
-        public boolean getHideClasses ()
-        {
-            return m_hideClasses;
-        }
-
-        public void setColumnOrder (final int [] columnOrder)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (columnOrder != null && columnOrder.length != 0, "null/empty input: outEncoding");
-            
-            m_columnOrder = columnOrder;
-        }
-
-        public int [] getColumnOrder ()
-        {
-            return m_columnOrder;
-        }
-
-        public void setSortOrder (final int [] sortOrder)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (sortOrder != null, "null input: sortOrder");
-            
-            m_sortOrder = sortOrder;
-        }
-
-        public int [] getSortOrder ()
-        {
-            return m_sortOrder;
-        }
-
-        public void setMetrics (final IntIntMap metrics)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (metrics != null, "null input: metrics");
-            
-            m_metrics = metrics;
-        }
-
-        public IntIntMap getMetrics ()
-        {
-            return m_metrics;
-        }
-        
-        // TODO: toString/logging
-        
-        void validate () throws IllegalArgumentException
-        {
-            if ($assert.ENABLED)
-            {
-                $assert.ASSERT (m_outEncoding != null, "m_outEncoding not set");
-                $assert.ASSERT (m_outDir != null || m_outFile != null, "either m_outDir or m_outFile must be set");
-                $assert.ASSERT (m_columnOrder != null, "m_columnOrder not set");
-                $assert.ASSERT (m_sortOrder != null, "m_sortOrder not set");
-                $assert.ASSERT (m_metrics != null, "m_metrics not set");
-            }
-        }
-
-
-        private String m_outEncoding;
-        private File m_outDir;
-        private File m_outFile;
-        
-        private int m_unitsType;
-        private int m_viewType;
-        
-        private boolean m_hideClasses;
-        private int m_depth;
-        
-        // TODO: fraction/number format strings...
-        
-        private int [] m_columnOrder; // attribute IDs [order indicates column order] 
-        private int [] m_sortOrder; // if m_sortOrder[i+1]>0 , sort m_columnOrder[m_sortOrder[i]] in ascending order
-        private IntIntMap m_metrics; // pass criteria (column attribute ID -> metric)
-        
-    } // end of nested class
-    
-    
-//    /**
-//     * Creates a property view specific to 'reportType' report type.
-//     * 
-//     * @param appProperties
-//     * @param reportType
-//     * @return
-//     */
-//    public static Properties getReportProperties (final Properties appProperties, final String reportType)
-//    {
-//        if ((reportType == null) || (reportType.length () == 0))
-//             throw new IllegalArgumentException ("null/empty input: reportType");
-//
-//        if (appProperties == null) return new XProperties ();
-//             
-//        return new ReportPropertyLookup (appProperties, reportType);
-//    }
-    
-    
-//    /**
-//     * @param type [null/empty indicates type-neutral property]
-//     */
-//    public static String getReportProperty (final String type, final Map properties, final String key)
-//    {
-//        if (properties == null) throw new IllegalArgumentException ("null input: properties");
-//        if (key == null) throw new IllegalArgumentException ("null input: key");
-//        
-//        String fullKey;
-//        
-//        if ((type == null) || (type.length () == 0))
-//            fullKey = IReportParameters.PREFIX.concat (key);
-//        else
-//        {
-//            fullKey = IReportParameters.PREFIX.concat (type).concat (".").concat (key);
-//            
-//            if (! properties.containsKey (fullKey)) // default to type-neutral lookup
-//                fullKey = IReportParameters.PREFIX.concat (key);
-//        }
-//            
-//        return (String) properties.get (fullKey);        
-//    }
-//    
-//    public static String getReportParameter (final String type, final Map properties, final String key, final String def)
-//    {
-//        final String value = getReportProperty (type, properties, key);
-//        
-//        return (value == null) ? def : value; 
-//    }
-
-    
-    public static ParsedProperties parseProperties (final IProperties properties, final String type)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (properties != null, "properties = null");
-        
-        final ParsedProperties result = new ParsedProperties ();
-        {
-            result.setOutEncoding (getReportProperty (properties, type, IReportProperties.OUT_ENCODING, false));
-        }
-        
-        // TODO: outDirName is no longer supported
-        
-        {
-            final String outDirName = getReportProperty (properties, type, IReportProperties.OUT_DIR, true);
-            final String outFileName = getReportProperty (properties, type, IReportProperties.OUT_FILE, false);
-    
-            // renormalize the out dir and file combination:
-        
-            if (outFileName != null)
-            {
-                final File fullOutFile = Files.newFile (outDirName, outFileName);
-                
-                final File dir = fullOutFile.getParentFile ();
-                if (dir != null) result.setOutDir (dir);
-            
-                result.setOutFile (new File (fullOutFile.getName ()));
-            }
-            else if (outDirName != null)
-            {
-                result.setOutDir (new File (outDirName));
-            }
-        }
-
-        {
-            final String unitsType = getReportProperty (properties, type, IReportProperties.UNITS_TYPE, true, IReportProperties.DEFAULT_UNITS_TYPE);
-            result.setUnitsType (IReportProperties.COUNT_UNITS.equals (unitsType) ? IItemAttribute.UNITS_COUNT : IItemAttribute.UNITS_INSTR);
-            
-            // TODO: invalid setting not checked
-        }
-        {
-            /* view type is no longer a user-overridable property [it is driven by SourceFile attribute presence]
-
-            final String viewType = getReportProperty (properties, type, IReportProperties.VIEW_TYPE, IReportProperties.DEFAULT_VIEW_TYPE);
-            result.setViewType (IReportProperties.SRC_VIEW.equals (viewType) ? IReportDataView.HIER_SRC_VIEW : IReportDataView.HIER_CLS_VIEW);
-            */
-            
-            result.setViewType (IReportDataView.HIER_SRC_VIEW);
-        } 
-        
-        {
-            final String hideClasses = getReportProperty (properties, type, IReportProperties.HIDE_CLASSES, true, IReportProperties.DEFAULT_HIDE_CLASSES);
-            result.setHideClasses (Property.toBoolean (hideClasses));
-        
-            // TODO: log this
-            if (result.getViewType () == IReportDataView.HIER_CLS_VIEW)
-                result.setHideClasses (false);
-        }
-        {
-            final String depth = getReportProperty (properties, type, IReportProperties.DEPTH, false, IReportProperties.DEFAULT_DEPTH);
-            
-            if (IReportProperties.DEPTH_ALL.equals (depth))
-                result.setDepth (AllItem.getTypeMetadata ().getTypeID ());
-            else if (IReportProperties.DEPTH_PACKAGE.equals (depth))
-                result.setDepth (PackageItem.getTypeMetadata ().getTypeID ());
-            else if (IReportProperties.DEPTH_SRCFILE.equals (depth))
-                result.setDepth (SrcFileItem.getTypeMetadata ().getTypeID ());
-            else if (IReportProperties.DEPTH_CLASS.equals (depth))
-                result.setDepth (ClassItem.getTypeMetadata ().getTypeID ());
-            else if (IReportProperties.DEPTH_METHOD.equals (depth))
-                result.setDepth (MethodItem.getTypeMetadata ().getTypeID ());
-            else
-                // TODO: properly prefixes prop name
-                throw new EMMARuntimeException (INVALID_PARAMETER_VALUE, new Object [] {IReportProperties.DEPTH, depth});
-        }
-        
-        if (result.getHideClasses () &&
-           (result.getViewType () == IReportDataView.HIER_SRC_VIEW) &&
-           (result.getDepth () == IItemMetadata.TYPE_ID_CLASS))
-        {
-            result.setDepth (IItemMetadata.TYPE_ID_SRCFILE);
-        }
-        
-        final Set /* String */ columnNames = new HashSet ();
-        {
-            final String columnList = getReportProperty (properties, type, IReportProperties.COLUMNS, false, IReportProperties.DEFAULT_COLUMNS);
-            final IntVector _columns = new IntVector ();
-            
-            final int [] out = new int [1];
-            
-            for (StringTokenizer tokenizer = new StringTokenizer (columnList, ","); tokenizer.hasMoreTokens (); )
-            {
-                final String columnName = tokenizer.nextToken ().trim ();
-                if (! COLUMNS.get (columnName, out))
-                {
-                    // TODO: generate the entire enum list in the err msg
-                    throw new EMMARuntimeException (INVALID_COLUMN_NAME, new Object [] {columnName});
-                }
-                
-                if (! REMOVE_DUPLICATE_COLUMNS || ! columnNames.contains (columnName))
-                {
-                    columnNames.add (columnName);
-                    _columns.add (out [0]);
-                }
-            }
-            
-            result.setColumnOrder (_columns.values ());
-        }
-        // [assertion: columnNames contains all columns for the report (some
-        // may get removed later by individual report generators if some debug info
-        // is missing)]
-        
-        {
-            final String sortList = getReportProperty (properties, type, IReportProperties.SORT, false, IReportProperties.DEFAULT_SORT);
-            final IntVector _sort = new IntVector ();
-            
-            final int [] out = new int [1];
-            
-            for (StringTokenizer tokenizer = new StringTokenizer (sortList, ","); tokenizer.hasMoreTokens (); )
-            {
-                final String sortSpec = tokenizer.nextToken ().trim ();
-                final String columnName;
-                final int dir;
-                
-                switch (sortSpec.charAt (0))
-                {
-                    case IReportProperties.ASC:
-                    {
-                        dir = +1;
-                        columnName = sortSpec.substring (1);
-                    }
-                    break;
-                    
-                    case IReportProperties.DESC:
-                    {
-                        dir = -1;
-                        columnName = sortSpec.substring (1);
-                    }
-                    break;
-                    
-                    default:
-                    {
-                        dir = +1;
-                        columnName = sortSpec;
-                    }
-                    break;
-                    
-                } // end of switch
-                
-                // silently ignore columns not in the column list:
-                if (columnNames.contains (columnName))
-                {
-                    COLUMNS.get (columnName, out);
-                    
-                    _sort.add (out [0]);    // sort attribute ID
-                    _sort.add (dir);        // sort direction
-                }
-                
-                result.setSortOrder (_sort.values ());
-            }
-        }
-        {
-            final String metricList = getReportProperty (properties, type, IReportProperties.METRICS, true, IReportProperties.DEFAULT_METRICS);
-            final IntIntMap _metrics = new IntIntMap ();
-            
-            final int [] out = new int [1];
-            
-            // TODO: perhaps should throw on invalid input here
-            for (StringTokenizer tokenizer = new StringTokenizer (metricList, ","); tokenizer.hasMoreTokens (); )
-            {
-                final String metricSpec = tokenizer.nextToken ().trim ();
-                final String columnName;
-                final double criterion;
-                
-                final int separator = metricSpec.indexOf (IReportProperties.MSEPARATOR);
-                if (separator > 0) // silently ignore invalid entries
-                {
-                    // silently ignore invalid cutoff values:
-                    try
-                    {
-                        criterion = Double.parseDouble (metricSpec.substring (separator + 1));
-                        if ((criterion < 0.0) || (criterion > 101.0)) continue;
-                    }
-                    catch (NumberFormatException nfe)
-                    {
-                        nfe.printStackTrace (System.out);
-                        continue;
-                    }
-                    
-                    columnName = metricSpec.substring (0, separator);
-                    
-                    // silently ignore columns not in the column list:
-                    if (columnNames.contains (columnName))
-                    {
-                        COLUMNS.get (columnName, out);
-                    
-                        _metrics.put (out [0], (int) Math.round (((criterion * IItem.PRECISION) / 100.0)));
-                    }
-                }
-            }
-                                        
-            result.setMetrics (_metrics);
-        }
-        
-        result.validate ();
-        
-        return result;
-    }
-
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final class ReportPropertyMapper implements IProperties.IMapper
-    {
-        public String getMappedKey (final String key)
-        {
-            if (key != null)
-            {
-                if (key.startsWith (IReportProperties.PREFIX))
-                {
-                    final int secondDot = key.indexOf ('.', IReportProperties.PREFIX.length ());
-                    if (secondDot > 0) 
-                    {
-                        // TODO: make this more precise (actually check the report type value string)
-                        
-                        return IReportProperties.PREFIX.concat (key.substring (secondDot + 1));
-                    }
-                }
-            }
-            
-            return null;
-        }
-
-    } // end of nested class
-    
-    
-//    private static final class ReportPropertyLookup extends XProperties
-//    {
-//        // note: due to incredibly stupid coding in java.util.Properties
-//        // (getProperty() uses a non-virtual call to super.get(), while propertyNames()
-//        // uses a virtual call to the same method instead of delegating to getProperty())
-//        // I must override both methods below
-//        
-//        public String getProperty (String key)
-//        {
-//            return (String) get (key);
-//        }
-//        
-//        // TODO: this kind of lookup makes the property listing confusing
-//        
-//        public Object get (final Object _key)
-//        {
-//            if (! (_key instanceof String)) return null;
-//            
-//            String key = (String) _key;
-//            
-//            if (key.startsWith (IReportProperties.PREFIX))
-//                key = key.substring (IReportProperties.PREFIX.length ());
-//            
-//            if (key.startsWith (m_reportType))
-//                key = key.substring (m_reportType.length () + 1);
-//             
-//            String fullKey = IReportProperties.PREFIX.concat (m_reportType).concat (".").concat (key);
-//            
-//            String result = defaults.getProperty (fullKey, null);
-//            if (result != null) return result;
-//            
-//            // fall back to report type-neutral namespace:
-//            fullKey = IReportProperties.PREFIX.concat (key);
-//            
-//            result = defaults.getProperty (fullKey, null);
-//            if (result != null) return result;
-//            
-//            return null;
-//        }
-//        
-//        
-//        ReportPropertyLookup (final Properties appProperties, final String reportType)
-//        {
-//            super (appProperties);
-//                 
-//            m_reportType = reportType;
-//        }
-//
-//        
-//        private final String m_reportType; // never null or empty [factory-ensured]
-//        
-//    } // end of nested class
-    
-    
-    private ReportProperties () {} // prevent subclassing
-    
-    
-    private static String getReportProperty (final IProperties properties, final String type, final String key, final boolean allowBlank)
-    {
-        return getReportProperty (properties, type, key, allowBlank, null);
-    }
-    
-    private static String getReportProperty (final IProperties properties, final String type, final String key, final boolean allowBlank, final String dflt)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (properties != null, "null input: properties");
-        if ($assert.ENABLED) $assert.ASSERT (key != null, "null input: key");
-        
-        final String result = properties.getProperty (IReportProperties.PREFIX.concat (type).concat (".").concat (key), dflt);
-        
-        if (! allowBlank && (result != null) && (result.trim ().length () == 0))
-            return dflt;
-        else
-            return result;
-    }
-
-    
-    private static final boolean REMOVE_DUPLICATE_COLUMNS = true;
-    private static final ObjectIntMap /* col name:String -> metadata:IItemMetadata */ COLUMNS; // set in <clinit>
-    
-    static
-    {
-        REPORT_PROPERTY_MAPPER = new ReportPropertyMapper ();
-        
-        final ObjectIntMap columns = new ObjectIntMap ();
-        
-        columns.put (IReportProperties.ITEM_NAME_COLUMN, IItemAttribute.ATTRIBUTE_NAME_ID);
-        columns.put (IReportProperties.CLASS_COVERAGE_COLUMN, IItemAttribute.ATTRIBUTE_CLASS_COVERAGE_ID);
-        columns.put (IReportProperties.METHOD_COVERAGE_COLUMN, IItemAttribute.ATTRIBUTE_METHOD_COVERAGE_ID);
-        columns.put (IReportProperties.BLOCK_COVERAGE_COLUMN, IItemAttribute.ATTRIBUTE_BLOCK_COVERAGE_ID);
-        columns.put (IReportProperties.LINE_COVERAGE_COLUMN, IItemAttribute.ATTRIBUTE_LINE_COVERAGE_ID);
-        
-        COLUMNS = columns;
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/SourcePathCache.java b/core/java12/com/vladium/emma/report/SourcePathCache.java
deleted file mode 100644
index 9d197ae..0000000
--- a/core/java12/com/vladium/emma/report/SourcePathCache.java
+++ /dev/null
@@ -1,228 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: SourcePathCache.java,v 1.1.1.1 2004/05/09 16:57:39 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.io.File;
-import java.io.FileFilter;
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class SourcePathCache
-{
-    // public: ................................................................
-    
-    // TODO: use soft cache for m_packageCache?
-    
-    /**
-     * @param sourcepath [can be empty]
-     */
-    public SourcePathCache (final String [] sourcepath, final boolean removeNonExistent)
-    {
-        if (sourcepath == null) throw new IllegalArgumentException ("null input: sourcepath");
-        
-        final List _sourcepath = new ArrayList (sourcepath.length);
-        for (int i = 0; i < sourcepath.length; ++ i)
-        {
-            final File dir = new File (sourcepath [i]);
-            
-            if (! removeNonExistent || (dir.isDirectory () && dir.exists ()))
-                _sourcepath.add (dir);
-        }
-        
-        m_sourcepath = new File [_sourcepath.size ()];
-        _sourcepath.toArray (m_sourcepath);
-        
-        m_packageCache = new HashMap ();
-    }
-    
-    /**
-     * @param sourcepath [can be empty]
-     */
-    public SourcePathCache (final File [] sourcepath, final boolean removeNonExistent)
-    {
-        if (sourcepath == null) throw new IllegalArgumentException ("null input: sourcepath");
-        
-        final List _sourcepath = new ArrayList (sourcepath.length);
-        for (int i = 0; i < sourcepath.length; ++ i)
-        {
-            final File dir = sourcepath [i];
-            
-            if (! removeNonExistent || (dir.isDirectory () && dir.exists ()))
-                _sourcepath.add (dir);
-        }
-        
-        m_sourcepath = new File [_sourcepath.size ()];
-        _sourcepath.toArray (m_sourcepath);
-        
-        m_packageCache = new HashMap ();
-    }
-    
-    /**
-     * @return absolute pathname [null if 'name' was not found in cache]
-     */
-    public synchronized File find (final String packageVMName, final String name)
-    {
-        if (packageVMName == null) throw new IllegalArgumentException ("null input: packageVMName");
-        if (name == null) throw new IllegalArgumentException ("null input: name");
-        
-        if (m_sourcepath.length == 0) return null;
-        
-        CacheEntry entry = (CacheEntry) m_packageCache.get (packageVMName);
-        
-        if (entry == null)
-        {
-            entry = new CacheEntry (m_sourcepath.length);
-            m_packageCache.put (packageVMName, entry);
-        }
-        
-        final Set [] listings = entry.m_listings;
-        for (int p = 0; p < listings.length; ++ p)
-        {
-            Set listing = listings [p];
-            if (listing == null)
-            {
-                listing = faultListing (m_sourcepath [p], packageVMName);
-                listings [p] = listing;
-            }
-            
-            // TODO: this is case-sensitive at this point
-            if (listing.contains (name))
-            {
-                final File relativeFile = new File (packageVMName.replace ('/', File.separatorChar), name);
-                
-                return new File (m_sourcepath [p], relativeFile.getPath ()).getAbsoluteFile ();
-            }
-        }
-        
-        return null;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final class CacheEntry
-    {
-        CacheEntry (final int size)
-        {
-            m_listings = new Set [size];
-        }
-        
-        
-        final Set /* String */ [] m_listings;
-        
-    } // end of nested class
-    
-    
-    // NOTE: because java.io.* implements file filtering in bytecode
-    // there is no real perf advantage in using a filter here (I might
-    // as well do list() and filter the result myself 
-    
-    private static final class FileExtensionFilter implements FileFilter
-    {
-        public boolean accept (final File file)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (file != null, "file = null");
-            
-            if (file.isDirectory ()) return false; // filter out directories
-
-            final String name = file.getName ();
-            final int lastDot = name.lastIndexOf ('.');
-            if (lastDot <= 0) return false;
-            
-            // [assertion: lastDot > 0]
-            
-            // note: match is case sensitive
-            return m_extension.equals (name.substring (lastDot));
-        }
-        
-        public String toString ()
-        {
-            return super.toString () + ", extension = [" + m_extension + "]";
-        }
-        
-        FileExtensionFilter (final String extension)
-        {
-            if (extension == null)
-                throw new IllegalArgumentException ("null input: extension");
-            
-            // ensure starting '.':
-            final String canonical = canonicalizeExtension (extension); 
-            
-            if (extension.length () <= 1)
-                throw new IllegalArgumentException ("empty input: extension");
-            
-            m_extension = canonical;
-        }
-        
-        private static String canonicalizeExtension (final String extension)
-        {
-            if (extension.charAt (0) != '.')
-                return ".".concat (extension);
-            else
-                return extension;
-        }
-        
-        
-        private final String m_extension;
-        
-    } // end of nested class
-    
-    
-    private Set /* String */ faultListing (final File dir, final String packageVMName)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (dir != null, "dir = null");
-        if ($assert.ENABLED) $assert.ASSERT (packageVMName != null, "packageVMName = null");
-        
-        final File packageFile = new File (dir, packageVMName.replace ('/', File.separatorChar));
-        
-        final File [] listing = packageFile.listFiles (FILE_EXTENSION_FILTER);
-        
-        if ((listing == null) || (listing.length == 0))
-            return Collections.EMPTY_SET;
-        else
-        {
-            final Set result = new HashSet (listing.length);
-            for (int f = 0; f < listing.length; ++ f)
-            {
-                result.add (listing [f].getName ());
-            }
-            
-            return result;
-        }
-    }
-    
-
-    private final File [] m_sourcepath; // never null
-    private final Map /* packageVMName:String->CacheEntry */ m_packageCache; // never null
-    
-    private static final FileExtensionFilter FILE_EXTENSION_FILTER; // set in <clinit>
-    
-    static
-    {
-        FILE_EXTENSION_FILTER = new FileExtensionFilter (".java");
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/SrcFileItem.java b/core/java12/com/vladium/emma/report/SrcFileItem.java
deleted file mode 100644
index 4b06847..0000000
--- a/core/java12/com/vladium/emma/report/SrcFileItem.java
+++ /dev/null
@@ -1,303 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: SrcFileItem.java,v 1.1.1.1.2.1 2004/06/20 20:07:22 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.util.Iterator;
-
-import com.vladium.util.IntObjectMap;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.data.ClassDescriptor;
-import com.vladium.emma.data.MethodDescriptor;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class SrcFileItem extends Item
-{
-    // public: ................................................................
-    
-    
-    public final class LineCoverageData
-    {
-        public static final int LINE_COVERAGE_ZERO = 0;
-        public static final int LINE_COVERAGE_PARTIAL = 1;
-        public static final int LINE_COVERAGE_COMPLETE = 2;
-        
-        public final int m_coverageStatus;
-        public final int [/* units mode */][/* total, coverage */] m_coverageRatio; // not null in LINE_COVERAGE_PARTIAL status only]
-        
-        LineCoverageData (final int coverageStatus, final int [][] coverageRatio)
-        {
-            m_coverageStatus = coverageStatus;
-            m_coverageRatio = coverageRatio;
-        }
-        
-    } // end of nested class
-    
-
-    public SrcFileItem (final IItem parent, final String name, final String fullVMName)
-    {
-        super (parent);
-        
-        m_name = name;
-        m_fullVMName = fullVMName;
-    }
-    
-    public String getName ()
-    {
-        return m_name;
-    }
-    
-    public String getFullVMName ()
-    {
-        return m_fullVMName;
-    }
-    
-    public int getFirstLine ()
-    {
-        // TODO: state validation
-        
-        if (m_firstLine == 0)
-        {
-            getAggregate (TOTAL_LINE_COUNT); // fault line coverage calculation
-        }
-        
-        return m_firstLine;
-    }
-
-    
-    
-    
-    public IntObjectMap /* line_no:int -> LineCoverageData */ getLineCoverage ()
-    {
-        if (m_lineCoverage == null)
-        {
-            getAggregate (TOTAL_LINE_COUNT); // fault line coverage calculation
-        }   
-        
-        return m_lineCoverage;
-    }
-    
-        
-    public int getAggregate (final int type)
-    {
-        final int [] aggregates = m_aggregates;
-
-        int value = aggregates [type];
-        
-        if (value < 0)
-        {
-            switch (type)
-            {
-                case COVERAGE_CLASS_COUNT:
-                case    TOTAL_CLASS_COUNT:
-                {                    
-                    aggregates [TOTAL_CLASS_COUNT] = getChildCount ();
-                    
-                    value = 0;
-                    for (Iterator children = getChildren (); children.hasNext (); )
-                    {
-                        // SF BUG 972725: this was incorrectly using 'type' instead
-                        // of the COVERAGE_CLASS_COUNT aggregate type, making class
-                        // coverage computation dependent on the order of how item
-                        // nodes were traversed in report generators
-                        value += ((IItem) children.next ()).getAggregate (COVERAGE_CLASS_COUNT);
-                    }
-                    aggregates [COVERAGE_CLASS_COUNT] = value;
-
-                    return aggregates [type];
-                }
-                //break;
-                
-                
-                case TOTAL_SRCFILE_COUNT:
-                {
-                    return aggregates [TOTAL_SRCFILE_COUNT] = 1;
-                }
-                //break;
-                
-                
-                case COVERAGE_LINE_COUNT:
-                case    TOTAL_LINE_COUNT:
-                
-                case COVERAGE_LINE_INSTR:
-                {
-                    // line aggregate types are special when used on srcfile items:
-                    // unlike all others, they do not simply add up when the line
-                    // info is available; instead, lines from all classes belonging
-                    // to the same srcfile parent are set-merged 
-                    
-                    final IntObjectMap /* line -> int[2] */ fldata = new IntObjectMap ();
-                    
-                    for (Iterator classes = getChildren (); classes.hasNext (); )
-                    {
-                        final ClassItem cls = (ClassItem) classes.next ();
-                    
-                        final boolean [][] ccoverage = cls.getCoverage (); // this can be null
-                        final ClassDescriptor clsdesc = cls.getClassDescriptor ();
-                        final MethodDescriptor [] methoddescs = clsdesc.getMethods ();
-                        
-                        for (Iterator methods = cls.getChildren (); methods.hasNext (); )
-                        {
-                            final MethodItem method = (MethodItem) methods.next ();
-                            final int methodID = method.getID ();
-                            
-                            final boolean [] mcoverage = ccoverage == null ? null : ccoverage [methodID];
-                            
-                            final MethodDescriptor methoddesc = methoddescs [methodID];                        
-                            final int [] mbsizes = methoddesc.getBlockSizes ();
-                            final IntObjectMap mlineMap = methoddesc.getLineMap ();
-                            if ($assert.ENABLED) $assert.ASSERT (mlineMap != null);
-                            
-                            final int [] mlines = mlineMap.keys ();
-                            for (int ml = 0, mlLimit = mlines.length; ml < mlLimit; ++ ml)
-                            {
-                                final int mline = mlines [ml];
-                                
-                                int [] data = (int []) fldata.get (mline);
-                                if (data == null)
-                                {
-                                    data = new int [4]; // { totalcount, totalinstr, coveragecount, coverageinstr }
-                                    fldata.put (mline, data);
-                                }
-                                
-                                final int [] lblocks = (int []) mlineMap.get (mline);
-                                
-                                final int bCount = lblocks.length; 
-                                data [0] += bCount;
-                                
-                                for (int bID = 0; bID < bCount; ++ bID)
-                                {
-                                    final int block = lblocks [bID];
-                                    
-                                    final boolean bcovered = mcoverage != null && mcoverage [block];
-                                    final int instr = mbsizes [block];
-                                    
-                                    data [1] += instr;
-                                    if (bcovered)
-                                    {
-                                        ++ data [2];
-                                        data [3] += instr;
-                                    }
-                                }
-                            }
-                        }
-                    }
-                    
-                    final int lineCount = fldata.size ();
-                    
-                    aggregates [TOTAL_LINE_COUNT] = lineCount;
-                    
-                    int coverageLineCount = 0;
-                    int coverageLineInstr = 0;
-                    
-                    final IntObjectMap /* line_no:int -> LineCoverageData */ lineCoverage = new IntObjectMap (lineCount);
-                    int firstLine = Integer.MAX_VALUE;
-                    
-                    final int [] clines = fldata.keys ();
-                    
-                    for (int cl = 0; cl < lineCount; ++ cl)
-                    {
-                        final int cline = clines [cl];
-                        final int [] data = (int []) fldata.get (cline);
-                        
-                        final int ltotalCount = data [0];
-                        final int ltotalInstr = data [1];
-                        final int lcoverageCount = data [2];
-                        final int lcoverageInstr = data [3];
-                        
-                        if (lcoverageInstr > 0)
-                        {
-                            coverageLineCount += (PRECISION * lcoverageCount) / ltotalCount;
-                            coverageLineInstr += (PRECISION * lcoverageInstr) / ltotalInstr;
-                        }
-                        
-                        // side effect: populate line coverage data map [used by getLineCoverage()]
-                        
-                        final int lcoverageStatus;
-                        int [][] lcoverageRatio = null;
-                        
-                        if (lcoverageInstr == 0)
-                            lcoverageStatus = LineCoverageData.LINE_COVERAGE_ZERO;
-                        else if (lcoverageInstr == ltotalInstr)
-                            lcoverageStatus = LineCoverageData.LINE_COVERAGE_COMPLETE;
-                        else
-                        {
-                            lcoverageStatus = LineCoverageData.LINE_COVERAGE_PARTIAL;
-                            lcoverageRatio = new int [][] {{ltotalCount, lcoverageCount}, {ltotalInstr, lcoverageInstr}}; // note: ordering depends on IItemAttribute.UNITS_xxx 
-                        }
-                        
-                        lineCoverage.put (cline, new LineCoverageData (lcoverageStatus, lcoverageRatio));
-                        
-                        // side effect: compute m_firstLine
-                        
-                        if (cline < firstLine) firstLine = cline;
-                    }
-                    
-                    m_lineCoverage = lineCoverage; // side effect
-                    m_firstLine = firstLine; // side effect
-                    
-                    aggregates [COVERAGE_LINE_COUNT] = coverageLineCount;
-                    aggregates [COVERAGE_LINE_INSTR] = coverageLineInstr;
-                    
-                    return aggregates [type];
-                }
-                //break;
-
-                            
-                default: return super.getAggregate (type);
-            }
-        }
-        
-        return value;
-    }
-
-    
-    public void accept (final IItemVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public final IItemMetadata getMetadata ()
-    {
-        return METADATA;
-    }
-    
-    public static IItemMetadata getTypeMetadata ()
-    {
-        return METADATA;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-    
-    
-    private final String m_name, m_fullVMName;
-    private IntObjectMap /* line_no:int -> LineCoverageData */ m_lineCoverage;
-    private int m_firstLine;
-    
-    private static final Item.ItemMetadata METADATA; // set in <clinit>
-        
-    static
-    {
-        METADATA = new Item.ItemMetadata (IItemMetadata.TYPE_ID_SRCFILE, "srcfile",
-            1 << IItemAttribute.ATTRIBUTE_NAME_ID |
-            1 << IItemAttribute.ATTRIBUTE_CLASS_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_METHOD_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_BLOCK_COVERAGE_ID |
-            1 << IItemAttribute.ATTRIBUTE_LINE_COVERAGE_ID);
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/ReportGenerator.java b/core/java12/com/vladium/emma/report/html/ReportGenerator.java
deleted file mode 100644
index 7dd9195..0000000
--- a/core/java12/com/vladium/emma/report/html/ReportGenerator.java
+++ /dev/null
@@ -1,1640 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ReportGenerator.java,v 1.2.2.1 2004/07/16 23:32:04 vlad_r Exp $
- */
-package com.vladium.emma.report.html;
-
-import java.io.BufferedReader;
-import java.io.BufferedWriter;
-import java.io.File;
-import java.io.FileOutputStream;
-import java.io.FileReader;
-import java.io.IOException;
-import java.io.OutputStreamWriter;
-import java.io.UnsupportedEncodingException;
-import java.text.DecimalFormat;
-import java.text.FieldPosition;
-import java.text.NumberFormat;
-import java.util.Date;
-import java.util.Iterator;
-import java.util.LinkedList;
-
-import com.vladium.util.Descriptors;
-import com.vladium.util.Files;
-import com.vladium.util.IProperties;
-import com.vladium.util.IntObjectMap;
-import com.vladium.util.IntVector;
-import com.vladium.util.ObjectIntMap;
-import com.vladium.util.Property;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMAProperties;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.data.ICoverageData;
-import com.vladium.emma.data.IMetaData;
-import com.vladium.emma.report.AbstractReportGenerator;
-import com.vladium.emma.report.AllItem;
-import com.vladium.emma.report.ClassItem;
-import com.vladium.emma.report.IItem;
-import com.vladium.emma.report.IItemAttribute;
-import com.vladium.emma.report.IItemMetadata;
-import com.vladium.emma.report.ItemComparator;
-import com.vladium.emma.report.MethodItem;
-import com.vladium.emma.report.PackageItem;
-import com.vladium.emma.report.SourcePathCache;
-import com.vladium.emma.report.SrcFileItem;
-import com.vladium.emma.report.html.doc.*;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class ReportGenerator extends AbstractReportGenerator
-                            implements IAppErrorCodes
-{
-    // public: ................................................................
-    
-    // TODO: make sure relative file names are converted to relative URLs in all anchors/hrefs
-
-    public ReportGenerator ()
-    {
-        m_format = (DecimalFormat) NumberFormat.getPercentInstance (); // TODO: locale
-        m_fieldPosition = new FieldPosition (DecimalFormat.INTEGER_FIELD);
-        
-        m_format.setMaximumFractionDigits (0);
-    }
-
-        
-    // IReportGenerator:
-    
-    public final String getType ()
-    {
-        return TYPE;
-    }
-    
-    public void process (final IMetaData mdata, final ICoverageData cdata,
-                         final SourcePathCache cache, final IProperties properties)
-        throws EMMARuntimeException
-    {
-        initialize (mdata, cdata, cache, properties);
-        
-        m_pageTitle = null;
-        m_footerBottom = null;
-        
-        File outDir = m_settings.getOutDir ();
-        if ((outDir == null) /* this should never happen */ || (outDir.equals (new File (Property.getSystemProperty ("user.dir", "")))))
-        {
-            outDir = new File ("coverage");
-            m_settings.setOutDir (outDir);
-        }        
-        
-        long start = 0, end;
-        final boolean trace1 = m_log.atTRACE1 ();
-        
-        if (trace1) start = System.currentTimeMillis ();
-        
-        {
-            m_queue = new LinkedList ();
-            m_reportIDNamespace = new IDGenerator (mdata.size ());
-            
-            for (m_queue.add (m_view.getRoot ()); ! m_queue.isEmpty (); )
-            {
-                final IItem head = (IItem) m_queue.removeFirst ();
-                
-                head.accept (this, null);
-            }
-            
-            m_reportIDNamespace = null;
-        }
-        
-        if (trace1)
-        {
-            end = System.currentTimeMillis ();
-            
-            m_log.trace1 ("process", "[" + getType () + "] report generated in " + (end - start) + " ms");
-        }
-    }
-    
-    public void cleanup ()
-    {
-        m_queue = null;
-        m_reportIDNamespace = null;
-        
-        super.cleanup ();
-    }
-
-        
-    // IItemVisitor:
-    
-    public Object visit (final AllItem item, final Object ctx)
-    {
-        HTMLWriter out = null;
-        try
-        {
-            File outFile = m_settings.getOutFile ();
-            if (outFile == null)
-            {
-                outFile = new File ("index".concat (FILE_EXTENSION));
-                m_settings.setOutFile (outFile);
-            }
-            
-            final File fullOutFile = Files.newFile (m_settings.getOutDir (), outFile);
-            
-            m_log.info ("writing [" + getType () + "] report to [" + fullOutFile.getAbsolutePath () + "] ...");
-            
-            out = openOutFile (fullOutFile, m_settings.getOutEncoding (), true);
-            
-            final int [] columns = m_settings.getColumnOrder ();
-            final StringBuffer buf = new StringBuffer ();
-            
-            final String title;
-            {
-                final StringBuffer _title = new StringBuffer (REPORT_HEADER_TITLE);
-                
-                _title.append (" (generated ");
-                _title.append (new Date (EMMAProperties.getTimeStamp ()));
-                _title.append (')');
-                
-                title = _title.toString ();
-            }
-            
-            final HTMLDocument page = createPage (title);            
-            {
-                final IItem [] path = getParentPath (item);
-                
-                addPageHeader (page, item, path);
-                addPageFooter (page, item, path);
-            }
-                        
-            // [all] coverage summary table:
-            
-            page.addH (1, "OVERALL COVERAGE SUMMARY", null);
-            
-            final HTMLTable summaryTable = new HTMLTable ("100%", null, null, "0");
-            {
-                // header row:
-                final HTMLTable.IRow header = summaryTable.newTitleRow ();
-                // coverage row:
-                final HTMLTable.IRow coverage = summaryTable.newRow ();
-                
-                for (int c = 0; c < columns.length; ++ c)
-                {
-                    final int attrID = columns [c];
-                    final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-                    
-                    final HTMLTable.ICell headercell = header.newCell ();
-                    headercell.setText (attr.getName (), true);
-                    
-                    if (attr != null)
-                    {
-                        boolean fail = (m_metrics [attrID] > 0) && ! attr.passes (item, m_metrics [attrID]);
-                        
-                        buf.setLength (0);
-                        attr.format (item, buf);
-                        
-                        final HTMLTable.ICell cell = coverage.newCell (); 
-                        cell.setText (buf.toString (), true);
-                        if (fail) cell.setClass (CSS_DATA_HIGHLIGHT);
-                    }
-                }
-            }
-            page.add (summaryTable);
-            
-            // [all] stats summary table ([all] only):
-
-            page.addH (2, "OVERALL STATS SUMMARY", null);
-            
-            final HTMLTable statsTable = new HTMLTable (null, null, null, "0");
-            statsTable.setClass (CSS_INVISIBLE_TABLE);
-            {
-                HTMLTable.IRow row = statsTable.newRow ();
-                row.newCell ().setText ("total packages:", true);
-                row.newCell ().setText ("" + item.getChildCount (), false);
-                
-                if (m_srcView && m_hasSrcFileInfo)
-                {
-                    row = statsTable.newRow ();
-                    row.newCell ().setText ("total executable files:", true);
-                    row.newCell ().setText ("" + item.getAggregate (IItem.TOTAL_SRCFILE_COUNT), false);
-                }
-                
-                row = statsTable.newRow ();
-                row.newCell ().setText ("total classes:", true);
-                row.newCell ().setText ("" + item.getAggregate (IItem.TOTAL_CLASS_COUNT), true);
-                row = statsTable.newRow ();
-                row.newCell ().setText ("total methods:", true);
-                row.newCell ().setText ("" + item.getAggregate (IItem.TOTAL_METHOD_COUNT), true);
-                
-                if (m_srcView && m_hasSrcFileInfo && m_hasLineNumberInfo)
-                {
-                    row = statsTable.newRow ();
-                    row.newCell ().setText ("total executable lines:", true);
-                    row.newCell ().setText ("" + item.getAggregate (IItem.TOTAL_LINE_COUNT), true);
-                }
-            }
-            /*
-            {
-                final HTMLTable.IRow first = statsTable.newRow (); // stats always available
-                
-                first.newCell ().setText ("total packages: " + item.getChildCount (), true);
-                first.newCell ().setText ("total classes: " + item.getAggregate (IItem.TOTAL_CLASS_COUNT), true);
-                first.newCell ().setText ("total methods: " + item.getAggregate (IItem.TOTAL_METHOD_COUNT), true);
-                
-                if (m_srcView && m_hasSrcFileInfo)
-                {
-                    final HTMLTable.IRow second = statsTable.newRow ();
-                    
-                    final HTMLTable.ICell cell1 = second.newCell ();
-                    cell1.setText ("total source files: " + item.getAggregate (IItem.TOTAL_SRCFILE_COUNT), true);
-                
-                    if (m_hasLineNumberInfo)
-                    {
-                        final HTMLTable.ICell cell2 = second.newCell ();
-                        
-                        cell2.setText ("total executable source lines: " + item.getAggregate (IItem.TOTAL_LINE_COUNT), true);
-                        cell2.getAttributes ().set (Attribute.COLSPAN, "2");
-                    }
-                    else
-                    {
-                        cell1.getAttributes ().set (Attribute.COLSPAN, "3");
-                    }
-                }
-            }
-            */
-            page.add (statsTable);
-            
-            final boolean deeper = (m_settings.getDepth () > item.getMetadata ().getTypeID ());
-            
-            // render package summary tables on the same page:
-            
-            page.addH (2, "COVERAGE BREAKDOWN BY PACKAGE", null);
-            
-            final HTMLTable childSummaryTable = new HTMLTable ("100%", null, null, "0");
-            {
-                int [] headerColumns = null;
-                
-                boolean odd = true;
-                final ItemComparator order = m_typeSortComparators [PackageItem.getTypeMetadata ().getTypeID ()];
-                for (Iterator packages = item.getChildren (order); packages.hasNext (); odd = ! odd)
-                {
-                    final IItem pkg = (IItem) packages.next ();
-                    
-                    if (headerColumns == null)
-                    {
-                        // header row:
-                        headerColumns = addHeaderRow (pkg, childSummaryTable, columns);                        
-                    }
-                    
-                    // coverage row:
-                    String childHREF = null;
-                    if (deeper)
-                    {
-                        childHREF = getItemHREF (item, pkg);
-                    }
-                    addItemRow (pkg, odd, childSummaryTable, headerColumns, childHREF, false);
-                    
-                    if (deeper) m_queue.addLast (pkg);
-                }
-            }
-            page.add (childSummaryTable);
-            
-            
-            page.emit (out);            
-            out.flush ();
-        }
-        finally
-        {
-            if (out != null) out.close ();
-            out = null;
-        }
-        
-        return ctx;
-    }
-    
-    public Object visit (final PackageItem item, final Object ctx)
-    {
-        HTMLWriter out = null;
-        try
-        {
-            if (m_verbose) m_log.verbose ("  report: processing package [" + item.getName () + "] ...");
-            
-            final File outFile = getItemFile (NESTED_ITEMS_PARENT_DIR, m_reportIDNamespace.getID (getItemKey (item)));
-            
-            out = openOutFile (Files.newFile (m_settings.getOutDir (), outFile), m_settings.getOutEncoding (), true);
-            
-            final int [] columns = m_settings.getColumnOrder ();            
-            final StringBuffer buf = new StringBuffer ();
-            
-            // TODO: set title [from a prop?]
-            final HTMLDocument page = createPage (REPORT_HEADER_TITLE);
-            {
-                final IItem [] path = getParentPath (item);
-                
-                addPageHeader (page, item, path);
-                addPageFooter (page, item, path);
-            }
-                        
-            // summary table:
-            
-            {
-                final IElement itemname = IElement.Factory.create (Tag.SPAN);
-                itemname.setText (item.getName (), true);
-                itemname.setClass (CSS_ITEM_NAME);
-                
-                final IElementList title = new ElementList ();
-                title.add (new Text ("COVERAGE SUMMARY FOR PACKAGE [", true));
-                title.add (itemname);
-                title.add (new Text ("]", true));
-                
-                page.addH (1, title, null);
-            }
-            
-            final HTMLTable summaryTable = new HTMLTable ("100%", null, null, "0");
-            {
-                // header row:
-                final HTMLTable.IRow header = summaryTable.newTitleRow ();
-                // coverage row:
-                final HTMLTable.IRow coverage = summaryTable.newRow ();
-                
-                for (int c = 0; c < columns.length; ++ c)
-                {
-                    final int attrID = columns [c];
-                    final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-                    
-                    final HTMLTable.ICell headercell = header.newCell ();
-                    headercell.setText (attr.getName (), true);
-                    
-                    if (attr != null)
-                    {
-                        boolean fail = (m_metrics [attrID] > 0) && ! attr.passes (item, m_metrics [attrID]);
-                        
-                        buf.setLength (0);
-                        attr.format (item, buf);
-                        
-                        final HTMLTable.ICell cell = coverage.newCell (); 
-                        cell.setText (buf.toString (), true);
-                        if (fail) cell.setClass (CSS_DATA_HIGHLIGHT);
-                    }
-                }
-            }
-            page.add (summaryTable);
-            
-            final boolean deeper = (m_settings.getDepth () > item.getMetadata ().getTypeID ());
-            
-            // render child summary tables on the same page:
-            
-            final String summaryTitle = m_srcView ? "COVERAGE BREAKDOWN BY SOURCE FILE" : "COVERAGE BREAKDOWN BY CLASS";
-            page.addH (2, summaryTitle, null);
-            
-            final HTMLTable childSummaryTable = new HTMLTable ("100%", null, null, "0");
-            {
-                int [] headerColumns = null;
-                
-                boolean odd = true;
-                final ItemComparator order = m_typeSortComparators [m_srcView ? SrcFileItem.getTypeMetadata ().getTypeID () : ClassItem.getTypeMetadata ().getTypeID ()];                
-                for (Iterator srcORclsFiles = item.getChildren (order); srcORclsFiles.hasNext (); odd = ! odd)
-                {
-                    final IItem srcORcls = (IItem) srcORclsFiles.next ();
-                    
-                    if (headerColumns == null)
-                    {
-                        // header row:
-                        headerColumns = addHeaderRow (srcORcls, childSummaryTable, columns);                        
-                    }
-                    
-                    // coverage row:
-                    String childHREF = null;
-                    if (deeper)
-                    {
-                        childHREF = getItemHREF (item, srcORcls);
-                    }
-                    addItemRow (srcORcls, odd, childSummaryTable, headerColumns, childHREF, false);
-                                        
-                    if (deeper) m_queue.addLast (srcORcls);
-                }
-            }
-            page.add (childSummaryTable);
-            
-            
-            page.emit (out);            
-            out.flush ();
-        }
-        finally
-        {
-            if (out != null) out.close ();
-            out = null;
-        }
-        
-        return ctx;
-    }
-
-    public Object visit (final SrcFileItem item, final Object ctx)
-    {
-        // this visit only takes place in src views
-        
-        HTMLWriter out = null;
-        try
-        {
-            final File outFile = getItemFile (NESTED_ITEMS_PARENT_DIR, m_reportIDNamespace.getID (getItemKey (item)));
-            
-            out = openOutFile (Files.newFile (m_settings.getOutDir (), outFile), m_settings.getOutEncoding (), true);
-            
-            final int [] columns = m_settings.getColumnOrder ();            
-            final StringBuffer buf = new StringBuffer ();
-            
-            // TODO: set title [from a prop?]
-            final HTMLDocument page = createPage (REPORT_HEADER_TITLE);
-            {
-                final IItem [] path = getParentPath (item);
-                
-                addPageHeader (page, item, path);
-                addPageFooter (page, item, path);
-            }
-            
-            // summary table:
-            
-            {
-                final IElement itemname = IElement.Factory.create (Tag.SPAN);
-                itemname.setText (item.getName (), true);
-                itemname.setClass (CSS_ITEM_NAME);
-                
-                final IElementList title = new ElementList ();
-                title.add (new Text ("COVERAGE SUMMARY FOR SOURCE FILE [", true));
-                title.add (itemname);
-                title.add (new Text ("]", true));
-                
-                page.addH (1, title, null);
-            }
-            
-            final HTMLTable summaryTable = new HTMLTable ("100%", null, null, "0");
-            {
-                // header row:
-                final HTMLTable.IRow header = summaryTable.newTitleRow ();
-                // coverage row:
-                final HTMLTable.IRow coverage = summaryTable.newRow ();
-                
-                for (int c = 0; c < columns.length; ++ c)
-                {
-                    final int attrID = columns [c];
-                    final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-                    
-                    final HTMLTable.ICell headercell = header.newCell ();
-                    headercell.setText (attr.getName (), true);
-                    
-                    if (attr != null)
-                    {
-                        boolean fail = (m_metrics [attrID] > 0) && ! attr.passes (item, m_metrics [attrID]);
-                        
-                        buf.setLength (0);
-                        attr.format (item, buf);
-                        
-                        final HTMLTable.ICell cell = coverage.newCell (); 
-                        cell.setText (buf.toString (), true);
-                        if (fail) cell.setClass (CSS_DATA_HIGHLIGHT);
-                    }
-                }
-            }
-            page.add (summaryTable);    
-            
-            final boolean deeper = (m_settings.getDepth () > ClassItem.getTypeMetadata ().getTypeID ());
-            final boolean embedSrcFile = deeper && srcFileAvailable (item, m_cache);
-            final boolean createAnchors = embedSrcFile && m_hasLineNumberInfo;
-            
-            final IDGenerator pageIDNamespace = createAnchors ? new IDGenerator () : null;
-            
-            // child summary table is special for srcfile items:
-            
-            page.addH (2, "COVERAGE BREAKDOWN BY CLASS AND METHOD", null);
-
-            final IntObjectMap lineAnchorIDMap = embedSrcFile ? new IntObjectMap () : null;
-            final HTMLTable childSummaryTable = new HTMLTable ("100%", null, null, "0");
-            
-            childSummaryTable.setClass (CSS_CLS_NOLEFT);
-            
-            {
-                int [] headerColumns = null;
-
-                final ItemComparator order = m_typeSortComparators [ClassItem.getTypeMetadata ().getTypeID ()];
-                int clsIndex = 0;                
-                for (Iterator classes = item.getChildren (order); classes.hasNext (); ++ clsIndex)
-                {
-                    final ClassItem cls = (ClassItem) classes.next ();
-
-                    if (headerColumns == null)
-                    {
-                        // header row:
-                        headerColumns = addHeaderRow (cls, childSummaryTable, columns);                        
-                    }
-                    
-                    String HREFname = null;
-                    
-                    // special class subheader:
-                    if (createAnchors)
-                    {
-                        if ($assert.ENABLED)
-                        {
-                            $assert.ASSERT (lineAnchorIDMap != null);
-                            $assert.ASSERT (pageIDNamespace != null);
-                        }
-                        
-                        final String childKey = getItemKey (cls);
-                        
-                        HREFname = addLineAnchorID (cls.getFirstLine (), pageIDNamespace.getID (childKey), lineAnchorIDMap);
-                    }
-
-                    addClassRow (cls, clsIndex, childSummaryTable, headerColumns, HREFname, createAnchors);
-                    
-//                    // row to separate this class's methods:
-//                    final HTMLTable.IRow subheader = childSummaryTable.newTitleRow ();
-//                    final HTMLTable.ICell cell = subheader.newCell ();
-//                    // TODO: cell.setColspan (???)
-//                    cell.setText ("class " + child.getName () + " methods:", true);
-                    
-                    boolean odd = false;
-                    final ItemComparator order2 = m_typeSortComparators [MethodItem.getTypeMetadata ().getTypeID ()];                
-                    for (Iterator methods = cls.getChildren (order2); methods.hasNext (); odd = ! odd)
-                    {
-                        final MethodItem method = (MethodItem) methods.next ();
-                        
-                        HREFname = null;
-                        
-                        if (createAnchors)
-                        {
-                            if ($assert.ENABLED)
-                            {
-                                $assert.ASSERT (lineAnchorIDMap != null);
-                                $assert.ASSERT (pageIDNamespace != null);
-                            }
-                            
-                            final String child2Key = getItemKey (method);
-                            
-                            HREFname = addLineAnchorID (method.getFirstLine (), pageIDNamespace.getID (child2Key), lineAnchorIDMap);
-                        }
-
-                        addClassItemRow (method, odd, childSummaryTable, headerColumns, HREFname, createAnchors);
-                    }
-                }
-            }
-            page.add (childSummaryTable);
-            
-            
-            // embed source file:
-             
-            if (deeper)
-            {
-                //page.addHR (1);
-                page.addEmptyP ();
-                {
-                    embedSrcFile (item, page, lineAnchorIDMap, m_cache);
-                }
-                //page.addHR (1);
-            }
-                
-            
-            page.emit (out);            
-            out.flush ();
-        }
-        finally
-        {
-            if (out != null) out.close ();
-            out = null;
-        }
-
-        return ctx;
-    }
-
-    public Object visit (final ClassItem item, final Object ctx)
-    {
-        // this visit only takes place in class views
-        
-        HTMLWriter out = null;
-        try
-        {
-            final File outFile = getItemFile (NESTED_ITEMS_PARENT_DIR, m_reportIDNamespace.getID (getItemKey (item)));
-            
-            // TODO: deal with overwrites
-            out = openOutFile (Files.newFile (m_settings.getOutDir (), outFile), m_settings.getOutEncoding (), true);
-            
-            final int [] columns = m_settings.getColumnOrder ();            
-            final StringBuffer buf = new StringBuffer ();
-            
-            // TODO: set title [from a prop?]
-            final HTMLDocument page = createPage (REPORT_HEADER_TITLE);
-            {
-                final IItem [] path = getParentPath (item);
-                
-                addPageHeader (page, item, path);
-                addPageFooter (page, item, path);
-            }
-            
-            
-            // summary table:
-            
-            {
-                final IElement itemname = IElement.Factory.create (Tag.SPAN);
-                itemname.setText (item.getName (), true);
-                itemname.setClass (CSS_ITEM_NAME);
-                
-                final IElementList title = new ElementList ();
-                title.add (new Text ("COVERAGE SUMMARY FOR CLASS [", true));
-                title.add (itemname);
-                title.add (new Text ("]", true));
-                
-                page.addH (1, title, null);
-            }
-            
-            final HTMLTable summaryTable = new HTMLTable ("100%", null, null, "0");
-            {
-                // header row:
-                final HTMLTable.IRow header = summaryTable.newTitleRow ();
-                // coverage row:
-                final HTMLTable.IRow coverage = summaryTable.newRow ();
-                
-                for (int c = 0; c < columns.length; ++ c)
-                {
-                    final int attrID = columns [c];
-                    final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-                    
-                    final HTMLTable.ICell headercell = header.newCell ();
-                    headercell.setText (attr.getName (), true);
-                    
-                    if (attr != null)
-                    {
-                        boolean fail = (m_metrics [attrID] > 0) && ! attr.passes (item, m_metrics [attrID]);
-                        
-                        buf.setLength (0);
-                        attr.format (item, buf);
-                        
-                        final HTMLTable.ICell cell = coverage.newCell (); 
-                        cell.setText (buf.toString (), true);
-                        if (fail) cell.setClass (CSS_DATA_HIGHLIGHT);
-                    }
-                }
-            }
-            page.add (summaryTable);
-            
-            
-            // child summary table:
-            
-            page.addH (2, "COVERAGE BREAKDOWN BY METHOD", null);
-
-            final HTMLTable childSummaryTable = new HTMLTable ("100%", null, null, "0");
-            {
-                int [] headerColumns = null;
-                
-                boolean odd = true;
-                final ItemComparator order = m_typeSortComparators [MethodItem.getTypeMetadata ().getTypeID ()];                
-                for (Iterator methods = item.getChildren (order); methods.hasNext (); odd = ! odd)
-                {
-                    final MethodItem method = (MethodItem) methods.next ();
-
-                    if (headerColumns == null)
-                    {
-                        // header row:
-                        headerColumns = addHeaderRow (method, childSummaryTable, columns);                        
-                    }
-                    
-                    addItemRow (method, odd, childSummaryTable, headerColumns, null, false);
-                }
-            }
-            page.add (childSummaryTable);
-            
-            
-            page.emit (out);            
-            out.flush ();
-        }
-        finally
-        {
-            if (out != null) out.close ();
-            out = null;
-        }
-
-        return ctx;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final class IDGenerator
-    {
-        IDGenerator ()
-        {
-            m_namespace = new ObjectIntMap (101);
-            m_out = new int [1];
-        }
-        
-        IDGenerator (final int initialCapacity)
-        {
-            m_namespace = new ObjectIntMap (initialCapacity);
-            m_out = new int [1];
-        }
-        
-        String getID (final String key)
-        {
-            final int [] out = m_out;
-            final int ID;
-            
-            if (m_namespace.get (key, out))
-                ID = out [0];
-            else
-            {
-                ID = m_namespace.size ();
-                m_namespace.put (key, ID);
-            }
-            
-            return Integer.toHexString (ID);
-        }
-        
-        private final ObjectIntMap /* key:String->ID */ m_namespace;
-        private final int [] m_out;
-        
-    } // end of nested class
-    
-    
-    private HTMLDocument createPage (final String title)
-    {
-        final HTMLDocument page = new HTMLDocument (title, m_settings.getOutEncoding ());
-        page.addStyle (CSS); // TODO: split by visit type
-        
-        return page;
-    }
-    
-    private IElement addPageHeader (final HTMLDocument page, final IItem item, final IItem [] path)
-    {
-        // TODO: merge header and footer in the same method
-        
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (page != null);
-        }
-        
-        final HTMLTable header = new HTMLTable ("100%", null, null, "0");
-        header.setClass (CSS_HEADER_FOOTER);
-
-        // header row:        
-        addPageHeaderTitleRow (header);
-        
-        // nav row:
-        {
-            final HTMLTable.IRow navRow = header.newRow ();
-            
-            final HTMLTable.ICell cell = navRow.newCell ();
-            cell.setClass (CSS_NAV);
-            
-            final int lLimit = path.length > 1 ? path.length - 1 : path.length;
-            for (int l = 0; l < lLimit; ++ l)
-            {
-                cell.add (LEFT_BRACKET);
-                
-                final String name = path [l].getName ();
-                final String HREF = getItemHREF (item, path [l]);
-                cell.add (new HyperRef (HREF, name, true));
-                
-                cell.add (RIGHT_BRACKET);
-            }
-        }
-        
-        page.setHeader (header);
-        
-        return header;
-    }
-    
-    private IElement addPageFooter (final HTMLDocument page, final IItem item, final IItem [] path)
-    {
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (page != null);
-        }
-
-        final HTMLTable footerTable = new HTMLTable ("100%", null, null, "0");
-        footerTable.setClass (CSS_HEADER_FOOTER);
-
-        // nav row:
-        {
-            final HTMLTable.IRow navRow = footerTable.newRow ();
-            
-            final HTMLTable.ICell cell = navRow.newCell ();
-            cell.setClass (CSS_NAV);
-            
-            final int lLimit = path.length > 1 ? path.length - 1 : path.length;
-            for (int l = 0; l < lLimit; ++ l)
-            {
-                cell.add (LEFT_BRACKET);
-                
-                final String name = path [l].getName ();
-                final String HREF = getItemHREF (item, path [l]);
-                cell.add (new HyperRef (HREF, name, true));
-                
-                cell.add (RIGHT_BRACKET);
-            }
-        }
-        
-        // title row:
-        {
-            final HTMLTable.IRow titleRow = footerTable.newRow ();
-            
-            final HTMLTable.ICell cell = titleRow.newCell ();
-            cell.setClass (CSS_TITLE);
-            
-            cell.add (getFooterBottom ());
-        }
-        
-        final ElementList footer = new ElementList ();
-        
-        footer.add (IElement.Factory.create (Tag.P)); // spacer
-        footer.add (footerTable);
-        
-        page.setFooter (footer);
-        
-        return footerTable;
-    }
-    
-    private int [] addHeaderRow (final IItem item, final HTMLTable table, final int [] columns)
-    {
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (item != null, "null input: item");
-            $assert.ASSERT (table != null, "null input: table");
-            $assert.ASSERT (columns != null, "null input: columns");
-        }
-        
-        // header row:
-        final HTMLTable.IRow header = table.newTitleRow ();
-        
-        // determine the set of columns actually present in the header [may be narrower than 'columns']:
-        final IntVector headerColumns = new IntVector (columns.length);
-        
-        for (int c = 0; c < columns.length; ++ c)
-        {
-            final int attrID = columns [c];
-            final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-            
-            if (attr != null)
-            {
-                final HTMLTable.ICell cell = header.newCell ();
-            
-                cell.setText (attr.getName (), true);//.getAttributes ().set (Attribute.WIDTH, "20%");
-                cell.setClass (headerCellStyle (c));
-                headerColumns.add (attrID);
-            }
-            
-            // note: by design this does not create columns for nonexistent attribute types
-        }
-        
-        return headerColumns.values ();
-    }
-    
-    /*
-     * No header row, just data rows.
-     */
-    private void addItemRow (final IItem item, final boolean odd, final HTMLTable table, final int [] columns, final String nameHREF, final boolean anchor)
-    {
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (item != null, "null input: item");
-            $assert.ASSERT (table != null, "null input: table");
-            $assert.ASSERT (columns != null, "null input: columns");
-        }
-        
-        final HTMLTable.IRow row = table.newRow ();
-        if (odd) row.setClass (CSS_ODDROW);
-        
-        final StringBuffer buf = new StringBuffer (11); // TODO: reuse a buffer
-        
-        for (int c = 0; c < columns.length; ++ c)
-        {
-            final int attrID = columns [c];
-            final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-            
-            if (attr != null)
-            {
-                final HTMLTable.ICell cell = row.newCell ();
-                
-                if ((nameHREF != null) && (attrID == IItemAttribute.ATTRIBUTE_NAME_ID))
-                {
-                    buf.setLength (0);
-                    attr.format (item, buf);
-                    
-                    trimForDisplay (buf);
-                    
-                    final String fullHREFName = anchor ? "#".concat (nameHREF) : nameHREF; 
-                    
-                    cell.add (new HyperRef (fullHREFName, buf.toString (), true));
-                }
-                else
-                {
-                    final boolean fail = (m_metrics [attrID] > 0) && ! attr.passes (item, m_metrics [attrID]);
-                    
-                    buf.setLength (0);
-                    attr.format (item, buf);
-                    
-                    trimForDisplay (buf);
-                     
-                    cell.setText (buf.toString (), true);
-                    if (fail) cell.setClass (CSS_DATA_HIGHLIGHT);
-                }
-            }
-            else
-            {
-                // note: by design this puts empty cells for nonexistent attribute types
-                
-                final HTMLTable.ICell cell = row.newCell (); 
-                cell.setText (" ", true);
-            }
-        }
-    }
-    
-    private void addClassRow (final ClassItem item, final int clsIndex, final HTMLTable table, final int [] columns,
-                              final String itemHREF, final boolean isAnchor)
-    {
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (item != null, "null input: item");
-            $assert.ASSERT (table != null, "null input: table");
-            $assert.ASSERT (columns != null, "null input: columns");
-        }
-        
-        final HTMLTable.IRow blank = table.newRow ();
-        
-        final HTMLTable.IRow row = table.newRow ();
-        row.setClass (CSS_CLASS_ITEM_SPECIAL);
-        
-        final StringBuffer buf = new StringBuffer (11);
-        
-        for (int c = 0; c < columns.length; ++ c)
-        {
-            final int attrID = columns [c];
-            final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-            
-            if (attr != null)
-            {
-                buf.setLength (0);
-                attr.format (item, buf);
-                
-                final HTMLTable.ICell blankcell = blank.newCell ();
-                blankcell.setClass (clsIndex == 0 ? CSS_BLANK : CSS_BOTTOM);
-                blankcell.setText (" ", true);
-                
-                final HTMLTable.ICell cell = row.newCell ();
-                
-                boolean fail = false;
-                if (attrID == IItemAttribute.ATTRIBUTE_NAME_ID)
-                {
-                    if (itemHREF != null)
-                    {
-                        final String fullItemHREF = isAnchor ? "#".concat (itemHREF) : itemHREF;
-                        
-                        cell.add (new Text ("class ", true));
-                        cell.add (new HyperRef (fullItemHREF, buf.toString (), true));
-                    }
-                    else
-                    {
-                        cell.setText ("class " + buf.toString (), true);
-                    }
-                }
-                else
-                {
-                    fail = (m_metrics [attrID] > 0) && ! attr.passes (item, m_metrics [attrID]);
-                    
-                    cell.setText (buf.toString (), true);
-                }
-                
-                cell.setClass (dataCellStyle (c, fail));
-            }
-            else
-            {
-                final HTMLTable.ICell cell = row.newCell (); 
-                cell.setText (" ", true);
-                cell.setClass (dataCellStyle (c, false));
-            }
-        }
-    }
-    
-    
-    private void addClassItemRow (final IItem item, final boolean odd, final HTMLTable table, final int [] columns, final String nameHREF, final boolean anchor)
-    {
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (item != null, "null input: item");
-            $assert.ASSERT (table != null, "null input: table");
-            $assert.ASSERT (columns != null, "null input: columns");
-        }
-        
-        final HTMLTable.IRow row = table.newRow ();
-        if (odd) row.setClass (CSS_ODDROW);
-        
-        final StringBuffer buf = new StringBuffer (11); // TODO: reuse a buffer
-        
-        for (int c = 0; c < columns.length; ++ c)
-        {
-            final int attrID = columns [c];
-            final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-            
-            if (attr != null)
-            {
-                final HTMLTable.ICell cell = row.newCell ();
-                
-                boolean fail = false;
-                if ((nameHREF != null) && (attrID == IItemAttribute.ATTRIBUTE_NAME_ID))
-                {
-                    buf.setLength (0);
-                    attr.format (item, buf);
-                    
-                    trimForDisplay (buf);
-                    
-                    final String fullHREFName = anchor ? "#".concat (nameHREF) : nameHREF; 
-                    
-                    cell.add (new HyperRef (fullHREFName, buf.toString (), true));
-                }
-                else
-                {
-                    fail = (m_metrics [attrID] > 0) && ! attr.passes (item, m_metrics [attrID]);
-                    
-                    buf.setLength (0);
-                    attr.format (item, buf);
-                    
-                    trimForDisplay (buf);
-                     
-                    cell.setText (buf.toString (), true);
-                }
-                
-                cell.setClass (dataCellStyle (c, fail));
-            }
-            else
-            {
-                // note: by design this puts empty cells for nonexistent attribute types
-                
-                final HTMLTable.ICell cell = row.newCell (); 
-                cell.setText (" ", true);
-                cell.setClass (dataCellStyle (c, false));
-            }
-        }
-    }
-    
-    
-    private boolean srcFileAvailable (final SrcFileItem item, final SourcePathCache cache)
-    {
-        if (cache == null) return false;
-        
-        if ($assert.ENABLED) $assert.ASSERT (item != null, "null input: item");
-        
-        final String fileName = item.getName ();
-        if ($assert.ENABLED) $assert.ASSERT (fileName.endsWith (".java"), "cache only handles .java extensions");
-        
-        // TODO: should I keep VM names in package items?
-        final String packageVMName = ((PackageItem) item.getParent ()).getVMName ();
-        
-        return (cache.find (packageVMName, fileName) != null);
-    }
-    
-//    private boolean srcFileAvailable (final ClassItem item, final SourcePathCache cache)
-//    {
-//        if (cache == null) return false;
-//        
-//        if ($assert.ENABLED) $assert.ASSERT (item != null, "null input: item");
-//        
-//        final String fileName = item.getSrcFileName ();
-//        if ($assert.ENABLED) $assert.ASSERT (fileName.endsWith (".java"), "cache only handles .java extensions");
-//        
-//        // TODO: should I keep VM names in package items?
-//        final String packageVMName = ((PackageItem) item.getParent ()).getVMName ();
-//        
-//        return (cache.find (packageVMName, fileName) != null);
-//    }
-    
-    private void embedSrcFile (final SrcFileItem item, final HTMLDocument page,
-                               final IntObjectMap /* line num:int->anchor name:String */anchorMap,
-                               final SourcePathCache cache)
-    {
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (item != null, "null input: item");
-            $assert.ASSERT (page != null, "null input: page");
-        }
-        
-        final String fileName = item.getName ();
-        if ($assert.ENABLED) $assert.ASSERT (fileName.endsWith (".java"), "cache only handles .java extensions");
-        
-        // TODO: should I keep VM names in package items?
-        final String packageVMName = ((PackageItem) item.getParent ()).getVMName ();
-        
-        boolean success = false;
-
-        final HTMLTable srcTable = new HTMLTable ("100%", null, null, "0");
-        
-        if (cache != null) // TODO: do this check earlier, in outer scope
-        {
-            srcTable.setClass (CSS_SOURCE);
-            final File srcFile = cache.find (packageVMName, fileName);
-            
-            if (srcFile != null)
-            {
-                BufferedReader in = null;
-                try
-                {
-                    in = new BufferedReader (new FileReader (srcFile), IO_BUF_SIZE);
-                    
-                    final boolean markupCoverage = m_hasLineNumberInfo;
-                    
-                    final int unitsType = m_settings.getUnitsType ();
-                    IntObjectMap /* line num:int -> SrcFileItem.LineCoverageData */ lineCoverageMap = null;
-                    StringBuffer tooltipBuffer = null;
-                    
-                    
-                    if (markupCoverage)
-                    {
-                        lineCoverageMap = item.getLineCoverage ();
-                        $assert.ASSERT (lineCoverageMap != null, "null: lineCoverageMap");
-                        
-                        tooltipBuffer = new StringBuffer (64);
-                    }
-                    
-                    int l = 1;
-                    for (String line; (line = in.readLine ()) != null; ++ l)
-                    {
-                        final HTMLTable.IRow srcline = srcTable.newRow ();
-                        final HTMLTable.ICell lineNumCell = srcline.newCell ();
-                        lineNumCell.setClass (CSS_LINENUM);
-                        
-                        if (anchorMap != null)
-                        {
-                            final int adjustedl = l < SRC_LINE_OFFSET ? l : l + SRC_LINE_OFFSET;
-                            
-                            final String anchor = (String) anchorMap.get (adjustedl);
-                            if (anchor != null)
-                            {
-                                final IElement a = IElement.Factory.create (Tag.A);
-                                //a.getAttributes ().set (Attribute.ID, anchor); ID anchoring does not work in NS 4.0
-                                a.getAttributes ().set (Attribute.NAME, anchor);
-                                
-                                a.setText (Integer.toString (l), true);
-                                
-                                lineNumCell.add (a);
-                            }
-                            else
-                            {
-                                lineNumCell.setText (Integer.toString (l), true);
-                            }
-                        }
-                        else
-                        {   
-                            lineNumCell.setText (Integer.toString (l), true);
-                        }
-                        
-                        final HTMLTable.ICell lineTxtCell = srcline.newCell ();
-                        lineTxtCell.setText (line.length () > 0 ? line : " ", true);
-                        
-                        if (markupCoverage)
-                        {
-                            final SrcFileItem.LineCoverageData lCoverageData = (SrcFileItem.LineCoverageData) lineCoverageMap.get (l);
-                            
-                            if (lCoverageData != null)
-                            {
-                                switch (lCoverageData.m_coverageStatus)
-                                {
-                                    case SrcFileItem.LineCoverageData.LINE_COVERAGE_ZERO:
-                                        srcline.setClass (CSS_COVERAGE_ZERO);
-                                    break;
-                                    
-                                    case SrcFileItem.LineCoverageData.LINE_COVERAGE_PARTIAL:
-                                    {
-                                        srcline.setClass (CSS_COVERAGE_PARTIAL);
-                                        
-                                        if (USE_LINE_COVERAGE_TOOLTIPS)
-                                        {
-                                            tooltipBuffer.setLength (0);
-                                            
-                                            final int [] coverageRatio = lCoverageData.m_coverageRatio [unitsType];
-                                            
-                                            final int d = coverageRatio [0];
-                                            final int n = coverageRatio [1];
-
-                                            m_format.format ((double) n / d, tooltipBuffer, m_fieldPosition);
-                                            
-                                            tooltipBuffer.append (" line coverage (");
-                                            tooltipBuffer.append (n);
-                                            tooltipBuffer.append (" out of ");
-                                            tooltipBuffer.append (d);
-
-                                            switch (unitsType)
-                                            {
-                                                case IItemAttribute.UNITS_COUNT:
-                                                    tooltipBuffer.append (" basic blocks)");
-                                                break;
-                                                
-                                                case IItemAttribute.UNITS_INSTR:
-                                                    tooltipBuffer.append (" instructions)");
-                                                break;
-                                            }                                            
-                                            
-                                            // [Opera does not display TITLE tooltios on <TR> elements]
-                                            
-                                            lineNumCell.getAttributes ().set (Attribute.TITLE, tooltipBuffer.toString ());
-                                            lineTxtCell.getAttributes ().set (Attribute.TITLE, tooltipBuffer.toString ());
-                                        }
-                                    }
-                                    break;
-                                        
-                                    case SrcFileItem.LineCoverageData.LINE_COVERAGE_COMPLETE:
-                                        srcline.setClass (CSS_COVERAGE_COMPLETE);
-                                    break;
-                                    
-                                    default: $assert.ASSERT (false, "invalid line coverage status: " + lCoverageData.m_coverageStatus);
-                                    
-                                } // end of switch
-                            }
-                        }
-                    }
-                    
-                    success = true;
-                }
-                catch (Throwable t)
-                {
-                    t.printStackTrace (System.out); // TODO: logging
-                    success = false;
-                }
-                finally
-                {
-                    if (in != null) try { in.close (); } catch (Throwable ignore) {}
-                    in = null;
-                }
-            }
-        }
-        
-        if (! success)
-        {
-            srcTable.setClass (CSS_INVISIBLE_TABLE);
-            
-            final HTMLTable.IRow row = srcTable.newTitleRow ();
-            row.newCell ().setText ("[source file '" + Descriptors.combineVMName (packageVMName, fileName) + "' not found in sourcepath]", false);
-        }
-        
-        page.add (srcTable);
-    }
-    
-    
-    private static String addLineAnchorID (final int line, final String anchorID,
-                                           final IntObjectMap /* line num:int->anchorID:String */lineAnchorIDMap)
-    {
-        if (line > 0)
-        {
-            final String _anchorID = (String) lineAnchorIDMap.get (line);
-            if (_anchorID != null)
-                return _anchorID;
-            else
-            {
-                lineAnchorIDMap.put (line, anchorID);
-
-                return anchorID;
-            }
-        }
-        
-        return null;
-    }
-    
-    /*
-     * Always includes AllItem
-     */
-    private IItem [] getParentPath (IItem item)
-    {
-        final LinkedList /* IItem */ _result = new LinkedList ();
-        
-        for ( ; item != null; item = item.getParent ())
-        {
-            _result.add (item);
-        }
-        
-        final IItem [] result = new IItem [_result.size ()];
-        int j = result.length - 1;
-        for (Iterator i = _result.iterator (); i.hasNext (); -- j)
-        {
-            result [j] = (IItem) i.next ();
-        }
-        
-        return result;
-    }
-
-    /*
-     * 
-     */
-    private String getItemHREF (final IItem base, final IItem item)
-    {
-        final String itemHREF;
-        if (item instanceof AllItem)
-            itemHREF = m_settings.getOutFile ().getName (); // note that this is always a simple filename [no parent path]
-        else
-            itemHREF = m_reportIDNamespace.getID (getItemKey (item)).concat (FILE_EXTENSION);
-             
-        final String fullHREF;
-        
-        if (base == null)
-            fullHREF = itemHREF;
-        else
-        {
-            final int nesting = NESTING [base.getMetadata ().getTypeID ()] [item.getMetadata ().getTypeID ()];
-            if (nesting == 1)
-                fullHREF = NESTED_ITEMS_PARENT_DIRNAME.concat ("/").concat (itemHREF);
-            else if (nesting == -1)
-                fullHREF = "../".concat (itemHREF);
-            else
-                fullHREF = itemHREF;
-        }
-        
-        return fullHREF;
-    }
-    
-    
-    private IContent getPageTitle ()
-    { 
-        IContent title = m_pageTitle;
-        if (title == null)
-        {
-            final IElementList _title = new ElementList ();
-            
-            _title.add (new HyperRef (IAppConstants.APP_HOME_SITE_LINK, IAppConstants.APP_NAME, true));
-            
-            final StringBuffer s = new StringBuffer (" Coverage Report (generated ");
-            s.append (new Date (EMMAProperties.getTimeStamp ()));
-            s.append (')');
-            
-            _title.add (new Text (s.toString (), true));
-            
-            m_pageTitle = title = _title;
-        }
-        
-        return title;
-    }
-    
-    private IContent getFooterBottom ()
-    { 
-        IContent bottom = m_footerBottom;
-        if (bottom == null)
-        {
-            final IElementList _bottom = new ElementList ();
-            
-            _bottom.add (new HyperRef (IAppConstants.APP_BUG_REPORT_LINK, IAppConstants.APP_NAME + " " + IAppConstants.APP_VERSION_WITH_BUILD_ID_AND_TAG, true));
-            _bottom.add (new Text (" " + IAppConstants.APP_COPYRIGHT, true));
-            
-            m_footerBottom = bottom = _bottom;
-        }
-        
-        return bottom;
-    }
-    
-    private void addPageHeaderTitleRow (final HTMLTable header)
-    {
-        final HTMLTable.IRow titleRow = header.newTitleRow ();
-        
-        final HTMLTable.ICell cell = titleRow.newCell ();
-        cell.setClass (CSS_TITLE);
-        cell.add (getPageTitle ());
-    }
-    
-    private static void trimForDisplay (final StringBuffer buf)
-    {
-        if (buf.length () > MAX_DISPLAY_NAME_LENGTH)
-        {
-            buf.setLength (MAX_DISPLAY_NAME_LENGTH - 3);
-            buf.append ("...");
-        }
-    }
-    
-    /*
-     * Assumes relative pathnames.
-     */
-    private static File getItemFile (final File parentDir, final String itemKey)
-    {
-        if (parentDir == null)
-            return new File (itemKey.concat (FILE_EXTENSION));
-        else
-            return new File (parentDir, itemKey.concat (FILE_EXTENSION));
-    }
-
-    private static String getItemKey (IItem item)
-    {
-        final StringBuffer result = new StringBuffer ();
-        
-        for ( ; item != null; item = item.getParent ())
-        {
-            result.append (item.getName ());
-            result.append (':');
-        }
-        
-        return result.toString ();
-    }
-
-    private static HTMLWriter openOutFile (final File file, final String encoding, final boolean mkdirs)
-    {
-        BufferedWriter out = null;
-        try
-        {
-            if (mkdirs)
-            {
-                final File parent = file.getParentFile ();
-                if (parent != null) parent.mkdirs ();
-            }
-            
-            out = new BufferedWriter (new OutputStreamWriter (new FileOutputStream (file), encoding), IO_BUF_SIZE);
-        }
-        catch (UnsupportedEncodingException uee)
-        {
-            // TODO: error code
-            throw new EMMARuntimeException (uee);
-        }
-        // note: in J2SDK 1.3 FileOutputStream constructor's throws clause
-        // was narrowed to FileNotFoundException:
-        catch (IOException fnfe) // FileNotFoundException  
-        {
-            // TODO: error code
-            throw new EMMARuntimeException (fnfe);
-        }
-        
-        return new HTMLWriter (out);
-    }
-    
-    private static String dataCellStyle (final int column, final boolean highlight)
-    {
-        if (column == 0)
-            return highlight ? CSS_DATA_HIGHLIGHT_FIRST : CSS_DATA_FIRST;
-        else
-            return highlight ? CSS_DATA_HIGHLIGHT : CSS_DATA;
-    }
-    
-    private static String headerCellStyle (final int column)
-    {
-        return (column == 0) ? CSS_HEADER_FIRST : CSS_HEADER;
-    }
-
-    
-    private final DecimalFormat m_format;
-    private final FieldPosition m_fieldPosition;
-        
-    private LinkedList /* IITem */ m_queue;
-    private IDGenerator m_reportIDNamespace;
-    
-    private IContent m_pageTitle, m_footerBottom;
-    
-    private static final boolean USE_LINE_COVERAGE_TOOLTIPS = true;
-    
-    private static final String TYPE = "html";
-    private static final String REPORT_HEADER_TITLE = IAppConstants.APP_NAME + " Coverage Report";
-    private static final IContent LEFT_BRACKET = new Text ("[", false);
-    private static final IContent RIGHT_BRACKET = new Text ("]", false);
-
-    private static final int MAX_DISPLAY_NAME_LENGTH = 80;
-    private static final int SRC_LINE_OFFSET = 4;
-    
-    
-    private static final String CSS_HEADER_FOOTER       = "hdft";
-    private static final String CSS_TITLE               = "tl";
-    private static final String CSS_NAV                 = "nv";
-    
-    private static final String CSS_COVERAGE_ZERO       = "z";
-    private static final String CSS_COVERAGE_PARTIAL    = "p";
-    private static final String CSS_COVERAGE_COMPLETE   = "c";
-    
-    private static final String DARKER_BACKGROUND   = "#F0F0F0";
-    private static final String TITLE_BACKGROUND    = "#6699CC";
-    private static final String NAV_BACKGROUND      = "#6633DD";
-    
-    private static final String CSS_INVISIBLE_TABLE     = "it";
-    
-    private static final String CSS_ITEM_NAME           = "in";
-    
-    private static final String CSS_CLASS_ITEM_SPECIAL  = "cis";
-    
-    private static final String CSS_SOURCE              = "s";
-    private static final String CSS_LINENUM             = "l";
-    
-    private static final String CSS_BOTTOM              = "bt";
-    private static final String CSS_ODDROW              = "o";
-    private static final String CSS_BLANK               = "b";
-    
-    private static final String CSS_DATA = "";
-    private static final String CSS_DATA_HIGHLIGHT = CSS_DATA + "h";
-    private static final String CSS_DATA_FIRST = CSS_DATA + "f";
-    private static final String CSS_DATA_HIGHLIGHT_FIRST = CSS_DATA + "hf";
-    private static final String CSS_HEADER = "";
-    private static final String CSS_HEADER_FIRST = CSS_HEADER + "f";
-    
-    private static final String CSS_CLS_NOLEFT          = "cn";
-    
-    // TODO: optimize this
-    
-    private static final String CSS =
-        " TABLE,TD,TH {border-style:solid; border-color:black;}" +
-        " TD,TH {background:white;margin:0;line-height:100%;padding-left:0.5em;padding-right:0.5em;}" +
-        
-        " TD {border-width:0 1px 0 0;}" +
-        " TH {border-width:1px 1px 1px 0;}" +
-        " TR TD." + CSS_DATA_HIGHLIGHT + " {color:red;}" +
-
-        " TABLE {border-spacing:0; border-collapse:collapse;border-width:0 0 1px 1px;}" +
-            
-        " P,H1,H2,H3,TH {font-family:verdana,arial,sans-serif;font-size:10pt;}" +
-        " TD {font-family:courier,monospace;font-size:10pt;}" + 
-         
-        " TABLE." + CSS_HEADER_FOOTER + " {border-spacing:0;border-collapse:collapse;border-style:none;}" + 
-        " TABLE." + CSS_HEADER_FOOTER + " TH,TABLE." + CSS_HEADER_FOOTER + " TD {border-style:none;line-height:normal;}" +
-        
-        " TABLE." + CSS_HEADER_FOOTER + " TH." + CSS_TITLE + ",TABLE." + CSS_HEADER_FOOTER + " TD." + CSS_TITLE + " {background:" + TITLE_BACKGROUND + ";color:white;}" +
-        " TABLE." + CSS_HEADER_FOOTER + " TD." + CSS_NAV + " {background:" + NAV_BACKGROUND + ";color:white;}" +
-                
-        " ." + CSS_NAV + " A:link {color:white;}" +
-        " ." + CSS_NAV + " A:visited {color:white;}" +
-        " ." + CSS_NAV + " A:active {color:yellow;}" +
-        
-        " TABLE." + CSS_HEADER_FOOTER + " A:link {color:white;}" +
-        " TABLE." + CSS_HEADER_FOOTER + " A:visited {color:white;}" +
-        " TABLE." + CSS_HEADER_FOOTER + " A:active {color:yellow;}" +
-        
-        //" ." + CSS_ITEM_NAME + " {color:#6633FF;}" + 
-        //" ." + CSS_ITEM_NAME + " {color:#C000E0;}" +
-        " ." + CSS_ITEM_NAME + " {color:#356085;}" +
-        
-        //" A:hover {color:#0066FF; text-decoration:underline; font-style:italic}" + 
-        
-        " TABLE." + CSS_SOURCE + " TD {padding-left:0.25em;padding-right:0.25em;}" +
-        " TABLE." + CSS_SOURCE + " TD." + CSS_LINENUM + " {padding-left:0.25em;padding-right:0.25em;text-align:right;background:" + DARKER_BACKGROUND + ";}" +
-        " TABLE." + CSS_SOURCE + " TR." + CSS_COVERAGE_ZERO + " TD {background:#FF9999;}" +
-        " TABLE." + CSS_SOURCE + " TR." + CSS_COVERAGE_PARTIAL + " TD {background:#FFFF88;}" +
-        " TABLE." + CSS_SOURCE + " TR." + CSS_COVERAGE_COMPLETE + " TD {background:#CCFFCC;}" +
-        
-        " A:link {color:#0000EE;text-decoration:none;}" + 
-        " A:visited {color:#0000EE;text-decoration:none;}" +
-        " A:hover {color:#0000EE;text-decoration:underline;}" +
-        
-        " TABLE." + CSS_CLS_NOLEFT + " {border-width:0 0 1px 0;}" +
-        " TABLE." + CSS_SOURCE + " {border-width:1px 0 1px 1px;}" +
-        
-//        " TD {border-width: 0px 1px 0px 0px; }" +
-        " TD." + CSS_DATA_HIGHLIGHT + " {color:red;border-width:0 1px 0 0;}" +
-        " TD." + CSS_DATA_FIRST + " {border-width:0 1px 0 1px;}" +
-        " TD." + CSS_DATA_HIGHLIGHT_FIRST + " {color:red;border-width:0 1px 0 1px;}" +
-
-//        " TH {border-width: 1px 1px 1px 0px; }" +        
-        " TH." + CSS_HEADER_FIRST + " {border-width:1px 1px 1px 1px;}" +
-
-        " TR." + CSS_CLASS_ITEM_SPECIAL + " TD {background:" + DARKER_BACKGROUND + ";}" +
-        " TR." + CSS_CLASS_ITEM_SPECIAL + " TD {border-width:1px 1px 1px 0;}" +
-        " TR." + CSS_CLASS_ITEM_SPECIAL + " TD." + CSS_DATA_HIGHLIGHT + " {color:red;border-width:1px 1px 1px 0;}" +        
-        " TR." + CSS_CLASS_ITEM_SPECIAL + " TD." + CSS_DATA_FIRST + " {border-width:1px 1px 1px 1px;}" +
-        " TR." + CSS_CLASS_ITEM_SPECIAL + " TD." + CSS_DATA_HIGHLIGHT_FIRST + " {color:red;border-width:1px 1px 1px 1px;}" +
-        
-        " TD." + CSS_BLANK + " {border-style:none;background:transparent;line-height:50%;} " +         
-        " TD." + CSS_BOTTOM + " {border-width:1px 0 0 0;background:transparent;line-height:50%;}" +
-        " TR." + CSS_ODDROW + " TD {background:" + DARKER_BACKGROUND + ";}" +
-        
-        "TABLE." + CSS_INVISIBLE_TABLE + " {border-style:none;}" +
-        "TABLE." + CSS_INVISIBLE_TABLE + " TD,TABLE." + CSS_INVISIBLE_TABLE + " TH {border-style:none;}" +
-        
-        "";
-
-    private static final String NESTED_ITEMS_PARENT_DIRNAME = "_files";
-    private static final File NESTED_ITEMS_PARENT_DIR = new File (NESTED_ITEMS_PARENT_DIRNAME);
-    private static final int [][] NESTING; // set in <clinit>; this reflects the dir structure for the report
-    
-    private static final String FILE_EXTENSION = ".html";
-    private static final int IO_BUF_SIZE = 32 * 1024;
-    
-    private static final long [] ATTRIBUTE_SETS; // set in <clinit>
-    
-    static
-    {
-        final IItemMetadata [] allTypes = IItemMetadata.Factory.getAllTypes (); 
-        
-        ATTRIBUTE_SETS = new long [allTypes.length];
-        for (int t = 0; t < allTypes.length; ++ t)
-        {
-            ATTRIBUTE_SETS [allTypes [t].getTypeID ()] = allTypes [t].getAttributeIDs ();
-        }
-        
-        NESTING = new int [4][4];
-        
-        int base = AllItem.getTypeMetadata().getTypeID (); 
-        NESTING [base][PackageItem.getTypeMetadata ().getTypeID ()] = 1;
-        NESTING [base][SrcFileItem.getTypeMetadata ().getTypeID ()] = 1;
-        NESTING [base][ClassItem.getTypeMetadata ().getTypeID ()] = 1;
-        
-        base = PackageItem.getTypeMetadata().getTypeID ();
-        NESTING [base][AllItem.getTypeMetadata ().getTypeID ()] = -1;
-        
-        base = SrcFileItem.getTypeMetadata().getTypeID ();
-        NESTING [base][AllItem.getTypeMetadata ().getTypeID ()] = -1;
-        
-        base = ClassItem.getTypeMetadata().getTypeID ();
-        NESTING [base][AllItem.getTypeMetadata ().getTypeID ()] = -1;
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/emma/report/html/doc/Attribute.java b/core/java12/com/vladium/emma/report/html/doc/Attribute.java
deleted file mode 100644
index 148cba2..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/Attribute.java
+++ /dev/null
@@ -1,101 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Attribute.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class Attribute implements IContent
-{
-    // public: ................................................................
-    
-    public static final Attribute ID = new AttributeImpl ("ID");
-    public static final Attribute NAME = new AttributeImpl ("NAME");
-    public static final Attribute TITLE = new AttributeImpl ("TITLE");
-    public static final Attribute TYPE = new AttributeImpl ("TYPE");
-    public static final Attribute CLASS = new AttributeImpl ("CLASS");
-    public static final Attribute HTTP_EQUIV = new AttributeImpl ("HTTP-EQUIV");
-    public static final Attribute CONTENT = new AttributeImpl ("CONTENT");
-    public static final Attribute HREF = new AttributeImpl ("HREF");
-    public static final Attribute SRC = new AttributeImpl ("SRC");
-    public static final Attribute REL = new AttributeImpl ("REL");
-    public static final Attribute WIDTH = new AttributeImpl ("WIDTH");
-    public static final Attribute SIZE = new AttributeImpl ("SIZE");
-    public static final Attribute BORDER = new AttributeImpl ("BORDER");
-    public static final Attribute CELLPADDING = new AttributeImpl ("CELLPADDING");
-    public static final Attribute CELLSPACING = new AttributeImpl ("CELLSPACING");
-    public static final Attribute ALIGN = new AttributeImpl ("ALIGN");
-    public static final Attribute COLSPAN = new AttributeImpl ("COLSPAN");
-    
-    public abstract String getName ();
-    
-    public abstract boolean equals (final Object rhs);
-    public abstract int hashCode ();
-    
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    Attribute () {}
-    
-    // private: ...............................................................
-    
-    
-    private static final class AttributeImpl extends Attribute
-    {
-        
-        public boolean equals (final Object rhs)
-        {
-            if (this == rhs) return true;
-            if (! (rhs instanceof AttributeImpl)) return false;
-            
-            return m_name.equals (((AttributeImpl) rhs).m_name); 
-        }
-        
-        public int hashCode ()
-        {
-            return m_name.hashCode ();
-        }
-        
-        public String toString ()
-        {
-            return m_name;
-        }
-        
-        public void emit (final HTMLWriter out)
-        {
-            out.write (m_name); // no need to escape anything
-        }
-        
-        public String getName ()
-        {
-            return m_name;
-        }
-        
-        
-        AttributeImpl (final String name)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (name != null, "name = null");
-            
-            m_name = name;
-        }
-
-        
-        private final String m_name;
-        
-    } // end of nested class 
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/AttributeSet.java b/core/java12/com/vladium/emma/report/html/doc/AttributeSet.java
deleted file mode 100644
index f49040c..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/AttributeSet.java
+++ /dev/null
@@ -1,117 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AttributeSet.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Map;
-
-import com.vladium.util.Strings;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class AttributeSet implements IContent
-{
-    // public: ................................................................
-    
-    public static AttributeSet create ()
-    {
-        return new AttributeSetImpl ();
-    }
-    
-    // ACCESSORS:
-    
-    public abstract boolean isEmpty ();
-    
-    // MUTATORS:
-    
-    public abstract AttributeSet set (Attribute attr, String value);
-    public abstract AttributeSet set (Attribute attr, int value);
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    AttributeSet () {}
-    
-    // private: ...............................................................
-    
-    
-    private static final class AttributeSetImpl extends AttributeSet
-    {
-        public void emit (final HTMLWriter out)
-        {
-            boolean first = true;
-            for (Iterator a = m_attrMap.entrySet ().iterator (); a.hasNext (); )
-            {
-                final Map.Entry entry = (Map.Entry) a.next ();
-                
-                final Attribute attr = (Attribute) entry.getKey ();
-                final String value = entry.getValue ().toString ();
-                
-                if (first)
-                    first = false;
-                else
-                    out.write (' ');
-                    
-                out.write (attr.getName ());
-                out.write ("=\"");
-
-                if ((m_buf != null) && (m_buf.length () <= MAX_BUF_LENGTH))
-                    m_buf.setLength (0);
-                else
-                    m_buf = new StringBuffer ();
-                
-                Strings.HTMLEscape (value, m_buf);
-                out.write (m_buf.toString ());
-                
-                out.write ('\"');
-            }
-        }
-        
-        public boolean isEmpty ()
-        {
-            return m_attrMap.isEmpty ();
-        }
-
-        
-        public AttributeSet set (final Attribute attr, final String value) // null removes?
-        {
-            m_attrMap.put (attr, value);
-            
-            return this;
-        }
-        
-        public AttributeSet set (final Attribute attr, final int value)
-        {
-            m_attrMap.put (attr, new Integer (value)); // TODO: use int factory here
-            
-            return this;
-        }
-        
-        
-        AttributeSetImpl ()
-        {
-            m_attrMap = new HashMap ();
-        }
-        
-        // TODO: consider lazy-initing this
-        private final Map /* Attribute->String|Integer */ m_attrMap; // never null
-        private StringBuffer m_buf; // reused by emit() 
-        
-        private static final int MAX_BUF_LENGTH = 4 * 1024;
-        
-    } // end of nested class
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/ElementList.java b/core/java12/com/vladium/emma/report/html/doc/ElementList.java
deleted file mode 100644
index c7bb87c..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/ElementList.java
+++ /dev/null
@@ -1,77 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ElementList.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-
-// ----------------------------------------------------------------------------
-/**
- * element list that is not necessarily an element itself
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class ElementList implements IElementList
-{
-    // public: ................................................................
-
-
-    public ElementList ()
-    {
-        m_contents = new ArrayList ();
-    }
-
-    
-    public void emit (final HTMLWriter out)
-    {
-        for (Iterator c = m_contents.iterator (); c.hasNext (); )
-        {
-            final IContent content = (IContent) c.next ();
-            content.emit (out);
-        }
-    }
-                
-    public IElementList add (final IContent content)
-    {
-        if (content != null)
-        {
-            m_contents.add (content);
-        }
-        
-        return this;
-    }
-    
-    public IElementList add (final int index, final IContent content)
-    {
-        if (content != null)
-        {
-            m_contents.add (index, content);
-        }
-        
-        return this;
-    }
-    
-    public int size ()
-    {
-        return m_contents.size ();
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private final List /* Content */ m_contents;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/HTMLDocument.java b/core/java12/com/vladium/emma/report/html/doc/HTMLDocument.java
deleted file mode 100644
index 7c2d27e..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/HTMLDocument.java
+++ /dev/null
@@ -1,200 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: HTMLDocument.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-import com.vladium.util.IConstants;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class HTMLDocument extends IElement.Factory.ElementImpl
-{
-    // public: ................................................................
-    
-
-    public HTMLDocument ()
-    {
-        this (null, null);
-    }
-    
-    public HTMLDocument (final String title, final String encoding)
-    {
-        super (Tag.HTML, AttributeSet.create ());
-        
-        super.add (m_head = IElement.Factory.create (Tag.HEAD));
-        super.add (m_body = IElement.Factory.create (Tag.BODY));
-
-        // specify encoding META before anything else:
-        if ((encoding != null) && (encoding.length () != 0))
-        {
-            final ISimpleElement meta = ISimpleElement.Factory.create (Tag.META);
-            
-            meta.getAttributes ()
-            .set (Attribute.HTTP_EQUIV, "Content-Type")
-            .set (Attribute.CONTENT, "text/html; charset=" + encoding);
-            
-            m_head.add (meta);
-        }
-        
-        if (title != null)
-        {
-            // TODO: escape
-            //getAttributes ().set (Attribute.TITLE, title);
-            
-            final IElement titleElement = IElement.Factory.create (Tag.TITLE).setText (title, false);
-            m_head.add (titleElement);            
-        }
-        
-        m_title = title;
-    }
-    
-    public String getTitle ()
-    {
-        return m_title;
-    }
-    
-    public IElement getHead ()
-    {
-        return m_head; 
-    }
-    
-    public IElement getBody ()
-    {
-        return m_body;
-    }
-    
-    public IContent getHeader ()
-    {
-        return m_header;
-    }
-    
-    public IContent getFooter ()
-    {
-        return m_footer;
-    }
-
-
-    public void setHeader (final IContent header)
-    {
-        if (header != null) m_header = header;
-    }
-    
-    public void setFooter (final IContent footer)
-    {
-        if (footer != null) m_footer = footer;
-    }
-
-    /**
-     * Overridden to ensure header/footer appear first/last in the body.
-     */
-    public void emit (HTMLWriter out)
-    {
-        if (m_header != null) m_body.add (0, m_header);
-        if (m_footer != null) m_body.add (m_body.size (), m_footer);
-            
-        super.emit(out);
-    }
-
-    /**
-     * Overridden to add to the doc body.
-     */
-    public IElementList add (final IContent content)
-    {
-        m_body.add (content);
-        
-        return this;
-    }
-    
-    public void addStyle (final String css)
-    {
-        if (css != null)
-        {
-            final IElement style = IElement.Factory.create (Tag.STYLE);
-            style.getAttributes ().set (Attribute.TYPE, "text/css");
-            
-            final StringBuffer def = new StringBuffer ("<!--");
-            def.append (IConstants.EOL);
-            
-            style.setText (css, false);
-            
-            def.append (IConstants.EOL);
-            def.append ("-->");
-            
-            m_head.add (style);
-        }
-    }
-    
-    /**
-     * Adds a &lt;LINK&gt; to the head.
-     */
-    public void addLINK (final String type, final String href)
-    {
-        final ISimpleElement link = ISimpleElement.Factory.create (Tag.LINK);
-        
-        // TODO: add REL="STYLESHEET"
-        
-        link.getAttributes ().set (Attribute.TYPE, type); // TODO: escape
-        link.getAttributes ().set (Attribute.HREF, href); // TODO: escape
-        link.getAttributes ().set (Attribute.SRC, href); // TODO: escape
-        
-        m_head.add (link);
-    }
-    
-    public void addH (final int level, final String text, final String classID)
-    {
-        final Tag Hl = Tag.Hs [level];
-        
-        final IElement h = IElement.Factory.create (Hl);
-        h.setText (text, true);
-        h.setClass (classID);
-         
-        add (h);
-    }
-    
-    public void addH (final int level, final IContent text, final String classID)
-    {
-        final Tag Hl = Tag.Hs [level];
-        
-        final IElement h = IElement.Factory.create (Hl);
-        h.add (text);
-        h.setClass (classID);
-         
-        add (h);
-    }
-    
-    public void addHR (final int size)
-    {
-        final IElement hr = IElement.Factory.create (Tag.HR);
-        hr.getAttributes ().set (Attribute.SIZE, size);
-        
-        add (hr);
-    }
-    
-    public void addEmptyP ()
-    {
-        add (IElement.Factory.create (Tag.P));
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private final String m_title;
-    private final IElement m_head;
-    private final IElement m_body;
-    
-    private IContent m_header, m_footer;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/HTMLTable.java b/core/java12/com/vladium/emma/report/html/doc/HTMLTable.java
deleted file mode 100644
index 70d5f83..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/HTMLTable.java
+++ /dev/null
@@ -1,132 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: HTMLTable.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class HTMLTable extends IElement.Factory.ElementImpl
-{
-    // public: ................................................................
-    
-    public static interface ICell extends IElement
-    {
-        ICell setColspan (final int span);
-        
-    } // end of nested interface
-    
-    public static interface IRow extends IElement
-    {
-        ICell newCell ();
-        
-    } // end of nested interface
-    
-    public HTMLTable (final String width, final String border, final String cellpadding, final String cellspacing)
-    {
-        super (Tag.TABLE, AttributeSet.create ());
-        
-        final AttributeSet attrs = getAttributes ();
-        
-        if (width != null) attrs.set (Attribute.WIDTH, width);
-        if (border != null) attrs.set (Attribute.BORDER, border);
-        if (cellpadding != null) attrs.set (Attribute.CELLPADDING, cellpadding);
-        if (cellspacing != null) attrs.set (Attribute.CELLSPACING, cellspacing);
-        
-        //m_rows = new LinkedList (); 
-    }
-    
-    public void setCaption (final String align, final String text, final boolean nbsp)
-    {
-        m_caption = IElement.Factory.create (Tag.CAPTION);
-        
-        m_caption.getAttributes ().set (Attribute.ALIGN, align);
-        m_caption.setText (text, nbsp);
-    }
-    
-    public IRow newTitleRow ()
-    {
-        final Row row = new Row (true);
-        add (row);
-        
-        return row;
-    }
-    
-    public IRow newRow ()
-    {
-        final Row row = new Row (false);
-        add (row);
-        
-        return row;
-    }
-    
-    public void emit (final HTMLWriter out)
-    {
-        if (m_caption != null)
-        {
-            add (0, m_caption);
-        }
-        
-        super.emit(out);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static class Cell extends IElement.Factory.ElementImpl
-                              implements ICell
-    {
-        public ICell setColspan (final int span)
-        {
-            getAttributes ().set (Attribute.COLSPAN, span);
-            
-            return this;
-        }
-        
-        Cell (Tag tag)
-        {
-            super (tag, AttributeSet.create ());
-        }
-                
-    } // end of nested class
-    
-    
-    private static class Row extends IElement.Factory.ElementImpl
-                             implements IRow
-    {
-        public ICell newCell ()
-        {
-            final ICell cell = new Cell (m_th ? Tag.TH : Tag.TD);
-            add (cell);
-            
-            return cell;
-        }
-        
-        Row (final boolean th)
-        {
-            super (Tag.TR, AttributeSet.create ());
-            
-            m_th = th;
-        }
-        
-        
-        private final boolean m_th;
-        
-    } // end of nested class
-    
-    
-    private IElement m_caption;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/HTMLWriter.java b/core/java12/com/vladium/emma/report/html/doc/HTMLWriter.java
deleted file mode 100644
index d9298c8..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/HTMLWriter.java
+++ /dev/null
@@ -1,119 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: HTMLWriter.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-import java.io.IOException;
-import java.io.Writer;
-
-import com.vladium.util.IConstants;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMARuntimeException;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class HTMLWriter
-{
-    // public: ................................................................
-    
-    // TODO: add API for indenting
-    
-    public HTMLWriter (final Writer out)
-    {
-        if (out == null) throw new IllegalArgumentException ("null input: out");
-        
-        m_out = out;
-    }
-    
-    
-    public void write (final String s)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (s != null, "s = null");
-        
-        if (m_out != null)
-        {
-            try
-            {
-                m_out.write (s);
-            }
-            catch (IOException ioe)
-            {
-                throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-            }
-        }
-    }
-    
-    public void write (final char c)
-    {
-        if (m_out != null)
-        {
-            try
-            {
-                m_out.write (c);
-            }
-            catch (IOException ioe)
-            {
-                throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-            }
-        }
-    }
-    
-    public void eol ()
-    {
-        if (m_out != null)
-        {
-            try
-            {
-                m_out.write (IConstants.EOL);
-            }
-            catch (IOException ioe)
-            {
-                throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-            }
-        }
-    }
-    
-    public void flush ()
-    {
-        if (m_out != null)
-        {
-            try
-            {
-                m_out.flush ();
-            }
-            catch (IOException ioe)
-            {
-                throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-            }
-        }
-    }
-    
-    public void close ()
-    {
-        if (m_out != null)
-        {
-            try { m_out.close (); } catch (IOException ignore) {}
-            m_out = null;
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private Writer m_out;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/HyperRef.java b/core/java12/com/vladium/emma/report/html/doc/HyperRef.java
deleted file mode 100644
index 8a4584a..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/HyperRef.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: HyperRef.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public class HyperRef extends IElement.Factory.ElementImpl
-{
-    // public: ................................................................
-    
-    public HyperRef (final String href, final String text, final boolean nbsp)
-    {
-        super (Tag.A, AttributeSet.create ());
-        
-        if ((href == null) || (href.length () == 0))
-            throw new IllegalArgumentException ("null or empty input: href");
-        
-        if ((text == null) || (text.length () == 0))
-            throw new IllegalArgumentException ("null or empty input: text");
-        
-        getAttributes ().set (Attribute.HREF, href);
-        
-        // TODO: does href need to be URL-encoded?
-        setText (text, nbsp); 
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/IContent.java b/core/java12/com/vladium/emma/report/html/doc/IContent.java
deleted file mode 100644
index 8ccaf40..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/IContent.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IContent.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IContent
-{
-    // public: ................................................................
-    
-    void emit (final HTMLWriter out);
-    
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/IElement.java b/core/java12/com/vladium/emma/report/html/doc/IElement.java
deleted file mode 100644
index a1e3ae0..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/IElement.java
+++ /dev/null
@@ -1,127 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IElement.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-import java.util.ArrayList;
-import java.util.Iterator;
-import java.util.List;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IElement extends ISimpleElement, IElementList
-{
-    // public: ................................................................
-    
-    IElement setText (String text, boolean nbsp); // size() is 0 after this
-    
-    abstract class Factory
-    {
-        public static IElement create (final Tag tag)
-        {
-            return new ElementImpl (tag, AttributeSet.create ());
-        }
-        
-        public static IElement create (final Tag tag, final AttributeSet attrs)
-        {
-            return new ElementImpl (tag, attrs);
-        }
-        
-        // TODO: should this extend ElementList?
-        static class ElementImpl extends ISimpleElement.Factory.SimpleElementImpl
-                                         implements IElement
-        {
-            public String toString ()
-            {
-                return "<" + m_tag.getName () + ">";
-            }
-            
-            public void emit (final HTMLWriter out)
-            {
-                final String tagName = m_tag.getName ();
-                
-                out.write ('<');
-                out.write (tagName);
-                
-                if (! m_attrs.isEmpty ())
-                {
-                    out.write (' ');
-                    m_attrs.emit (out);
-                }
-                
-                out.write ('>');
-                
-                for (Iterator c = m_contents.iterator (); c.hasNext (); )
-                {
-                    final IContent content = (IContent) c.next ();
-                    content.emit (out);
-                }
-                
-                out.write ("</");
-                out.write (tagName);
-                out.write ('>');
-                if (DEBUG_HTML) out.eol (); // using ENABLED as DEBUG here
-            }
-                        
-            public IElementList add (final IContent content)
-            {
-                if (content != null)
-                {
-                    m_contents.add (content);
-                }
-                
-                return this;
-            }
-            
-            public IElementList add (final int index, final IContent content)
-            {
-                if (content != null)
-                {
-                    m_contents.add (index, content);
-                }
-                
-                return this;
-            }
-            
-            public int size ()
-            {
-                return m_contents.size ();
-            }
-            
-            public IElement setText (final String text, final boolean nbsp)
-            {
-                if (text != null)
-                {
-                    m_contents.clear ();
-                    m_contents.add (new Text (text, nbsp));
-                }
-                
-                return this;
-            }
-            
-            ElementImpl (final Tag tag, final AttributeSet attrs)
-            {
-                super (tag, attrs);
-                
-                m_contents = new ArrayList ();
-            }
-
-            
-            protected final List /* Content */ m_contents;
-            
-            private static final boolean DEBUG_HTML = false;
-                    
-        } // end of nested class
-
-    } // end of nested class 
-    
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/IElementList.java b/core/java12/com/vladium/emma/report/html/doc/IElementList.java
deleted file mode 100644
index 4fa151b..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/IElementList.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IElementList.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IElementList extends IContent
-{
-    // public: ................................................................
-    
-    IElementList add (IContent content);
-    IElementList add (int index, IContent content);
-    int size (); // element count 
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/ISimpleElement.java b/core/java12/com/vladium/emma/report/html/doc/ISimpleElement.java
deleted file mode 100644
index 6d6c440..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/ISimpleElement.java
+++ /dev/null
@@ -1,99 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ISimpleElement.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface ISimpleElement extends IContent
-{
-    // public: ................................................................
-
-    Tag getTag ();
-    ISimpleElement setClass (String classID);
-    AttributeSet getAttributes ();     
-    
-    abstract class Factory
-    {
-        public static ISimpleElement create (final Tag tag)
-        {
-            return new SimpleElementImpl (tag, AttributeSet.create ());
-        }
-        
-        public static ISimpleElement create (final Tag tag, final AttributeSet attrs)
-        {
-            return new SimpleElementImpl (tag, attrs);
-        }
-        
-        static class SimpleElementImpl implements ISimpleElement
-        {
-            public String toString ()
-            {
-                return "<" + m_tag.getName () + "/>";
-            }
-            
-            public Tag getTag ()
-            {
-                return m_tag;
-            }
-            
-            public ISimpleElement setClass (final String classID)
-            {
-                if ((classID != null) && (classID.length () > 0))
-                {
-                    getAttributes ().set (Attribute.CLASS, classID);
-                }
-                
-                return this;
-            }
-            
-            public AttributeSet getAttributes ()
-            {
-                return m_attrs;
-            }
-    
-            public void emit (final HTMLWriter out)
-            {
-                out.write ('<');
-                out.write (m_tag.getName ());
-                
-                if (! m_attrs.isEmpty ())
-                {
-                    out.write (' ');
-                    m_attrs.emit (out);
-                }
-                
-                out.write ("/>");
-            }
-            
-            SimpleElementImpl (final Tag tag, final AttributeSet attrs)
-            {
-                if ($assert.ENABLED) $assert.ASSERT (tag != null, "tag = null");
-                if ($assert.ENABLED) $assert.ASSERT (attrs != null, "attrs = null");
-                
-                m_tag = tag;
-                m_attrs = attrs;
-            }
-            
-            
-            protected final Tag m_tag;
-            protected final AttributeSet m_attrs;
-            
-        } // end of nested class
-        
-    } // end of nested class
-    
-
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/Tag.java b/core/java12/com/vladium/emma/report/html/doc/Tag.java
deleted file mode 100644
index 94614bb..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/Tag.java
+++ /dev/null
@@ -1,92 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Tag.java,v 1.1.1.1 2004/05/09 16:57:41 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class Tag implements IContent
-{
-    // public: ................................................................
-    
-    public static final Tag HTML = new TagImpl ("HTML");
-    public static final Tag HEAD = new TagImpl ("HEAD");
-    public static final Tag BODY = new TagImpl ("BODY");
-    public static final Tag META = new TagImpl ("META");
-    public static final Tag STYLE = new TagImpl ("STYLE");
-    
-    public static final Tag TITLE = new TagImpl ("TITLE");
-    public static final Tag H1 = new TagImpl ("H1");
-    public static final Tag H2 = new TagImpl ("H2");
-    public static final Tag H3 = new TagImpl ("H3");
-    public static final Tag H4 = new TagImpl ("H4");
-    public static final Tag H5 = new TagImpl ("H5");
-    public static final Tag H6 = new TagImpl ("H6");
-    public static final Tag LINK = new TagImpl ("LINK");
-    
-    public static final Tag A = new TagImpl ("A");
-    
-    public static final Tag TABLE = new TagImpl ("TABLE");
-    public static final Tag CAPTION = new TagImpl ("CAPTION");
-    public static final Tag TH = new TagImpl ("TH");
-    public static final Tag TR = new TagImpl ("TR");
-    public static final Tag TD = new TagImpl ("TD");
-    
-    public static final Tag HR = new TagImpl ("HR");
-    public static final Tag P = new TagImpl ("P");
-    public static final Tag SPAN = new TagImpl ("SPAN");
-    
-    public static final Tag [] Hs = new Tag [] {H1, H2, H3, H4, H4, H6};
-    
-    public abstract String getName ();
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    Tag () {}
-    
-    // private: ...............................................................
-    
-    private static final class TagImpl extends Tag
-    {
-        public void emit (final HTMLWriter out)
-        {
-            out.write (m_name);
-        }
-        
-        public String getName ()
-        {
-            return m_name;
-        }
-        
-        public String toString ()
-        {
-            return m_name;
-        }
-        
-        TagImpl (final String name)
-        {
-            if ($assert.ENABLED) $assert.ASSERT (name != null, "name = null");
-            
-            m_name = name;
-        }
-        
-        
-        private final String m_name;
-        
-    } // end of 
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/Text.java b/core/java12/com/vladium/emma/report/html/doc/Text.java
deleted file mode 100644
index 5dc731e..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/Text.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Text.java,v 1.1.1.1 2004/05/09 16:57:42 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-import com.vladium.util.Strings;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public 
-final class Text implements IContent
-{
-    // public: ................................................................
-
-    public Text (final String text, final boolean nbsp)
-    {
-        m_text = text;
-        m_nbsp = nbsp;
-    }
-    
-    public void emit (final HTMLWriter out)
-    {
-        if (m_text != null)
-        {
-            if (m_nbsp)
-                out.write (Strings.HTMLEscapeSP (m_text));
-            else
-                out.write (Strings.HTMLEscape (m_text));
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private final String m_text;
-    private final boolean m_nbsp;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/html/doc/TextContent.java b/core/java12/com/vladium/emma/report/html/doc/TextContent.java
deleted file mode 100644
index 53c851c..0000000
--- a/core/java12/com/vladium/emma/report/html/doc/TextContent.java
+++ /dev/null
@@ -1,43 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: TextContent.java,v 1.1.1.1 2004/05/09 16:57:42 vlad_r Exp $
- */
-package com.vladium.emma.report.html.doc;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class TextContent implements IContent
-{
-    // public: ................................................................
-
-    public TextContent (final String text)
-    {
-        m_text = text;
-    }   
-
-    public void emit (final HTMLWriter out)
-    {
-        if (m_text != null)
-        {
-            out.write (m_text);
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private final String m_text;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/reportCommand.java b/core/java12/com/vladium/emma/report/reportCommand.java
deleted file mode 100644
index 5810657..0000000
--- a/core/java12/com/vladium/emma/report/reportCommand.java
+++ /dev/null
@@ -1,175 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: reportCommand.java,v 1.1.1.1.2.1 2004/07/16 23:32:29 vlad_r Exp $
- */
-package com.vladium.emma.report;
-
-import java.io.IOException;
-
-import com.vladium.util.ClassLoaderResolver;
-import com.vladium.util.Strings;
-import com.vladium.util.args.IOptsParser;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.Command;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMARuntimeException;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class reportCommand extends Command
-{
-    // public: ................................................................
-
-    public reportCommand (final String usageToolName, final String [] args)
-    {
-        super (usageToolName, args);
-    }
-
-    public synchronized void run ()
-    {
-        ClassLoader loader;
-        try
-        {
-            loader = ClassLoaderResolver.getClassLoader ();
-        }
-        catch (Throwable t)
-        {
-            loader = getClass ().getClassLoader ();
-        }
-        
-        try
-        {
-            // process 'args':
-            {
-                final IOptsParser parser = getOptParser (loader);
-                final IOptsParser.IOpts parsedopts = parser.parse (m_args);
-                
-                // check if usage is requested before checking args parse errors etc:
-                {
-                    final int usageRequestLevel = parsedopts.usageRequestLevel ();
-
-                    if (usageRequestLevel > 0)
-                    {
-                        usageexit (parser, usageRequestLevel, null);
-                        return;
-                    }
-                }
-                
-                final IOptsParser.IOpt [] opts = parsedopts.getOpts ();
-                
-                if (opts == null) // this means there were args parsing errors
-                {
-                    parsedopts.error (m_out, STDOUT_WIDTH);
-                    usageexit (parser, IOptsParser.SHORT_USAGE, null);
-                    return;
-                }
-                
-                // process parsed args:
-
-                try
-                {
-                    for (int o = 0; o < opts.length; ++ o)
-                    {
-                        final IOptsParser.IOpt opt = opts [o];
-                        final String on = opt.getCanonicalName ();
-                        
-                        if (! processOpt (opt))
-                        {
-                            if ("in".equals (on))
-                            {
-                                m_datapath = getListOptValue (opt, PATH_DELIMITERS, true);
-                            }
-                            else if ("sp".equals (on))
-                            {
-                                m_srcpath = getListOptValue (opt, PATH_DELIMITERS, true);
-                            }
-                            else if ("r".equals (on))
-                            {
-                                m_reportTypes = Strings.merge (opt.getValues (), COMMA_DELIMITERS, true);
-                            }
-                        }
-                    }
-                    
-                    // user '-props' file property overrides:
-                    
-                    if (! processFilePropertyOverrides ()) return;
-                    
-                    // process prefixed opts:
-                    
-                    processCmdPropertyOverrides (parsedopts);
-                }
-                catch (IOException ioe)
-                {
-                    throw new EMMARuntimeException (IAppErrorCodes.ARGS_IO_FAILURE, ioe);
-                }
-                
-                // handle cmd line-level defaults:
-                {
-                }
-            }
-            
-            // run the reporter:
-            {
-                final ReportProcessor processor = ReportProcessor.create ();
-                processor.setAppName (IAppConstants.APP_NAME); // for log prefixing
-                
-                processor.setDataPath (m_datapath);
-                processor.setSourcePath (m_srcpath);
-                if ($assert.ENABLED) $assert.ASSERT (m_reportTypes != null, "m_reportTypes no set");
-                processor.setReportTypes (m_reportTypes); // no "txt" default for report processor
-                processor.setPropertyOverrides (m_propertyOverrides);
-                
-                processor.run ();
-            }
-        }
-        catch (EMMARuntimeException yre)
-        {
-            // TODO: see below
-            
-            exit (true, yre.getMessage (), yre, RC_UNEXPECTED); // does not return
-            return;
-        }
-        catch (Throwable t)
-        {
-            // TODO: embed: OS/JVM fingerprint, build #, etc
-            // TODO: save stack trace in a file and prompt user to send it to ...
-            
-            exit (true, "unexpected failure: ", t, RC_UNEXPECTED); // does not return
-            return;
-        }
-
-        exit (false, null, null, RC_OK);
-    }    
-    
-    // protected: .............................................................
-
-
-    protected void initialize ()
-    {
-        super.initialize ();                
-    }
-    
-    protected String usageArgsMsg ()
-    {
-        return "[options]";
-    }
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private String [] m_datapath; // list of data files, not a real path
-    private String [] m_srcpath;
-    private String [] m_reportTypes;
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/txt/ReportGenerator.java b/core/java12/com/vladium/emma/report/txt/ReportGenerator.java
deleted file mode 100644
index aba41f9..0000000
--- a/core/java12/com/vladium/emma/report/txt/ReportGenerator.java
+++ /dev/null
@@ -1,528 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ReportGenerator.java,v 1.1.1.1.2.1 2004/07/16 23:32:30 vlad_r Exp $
- */
-package com.vladium.emma.report.txt;
-
-import java.io.BufferedWriter;
-import java.io.File;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.OutputStreamWriter;
-import java.io.UnsupportedEncodingException;
-import java.util.Date;
-import java.util.Iterator;
-import java.util.LinkedList;
-
-import com.vladium.util.Files;
-import com.vladium.util.IProperties;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMAProperties;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.data.ICoverageData;
-import com.vladium.emma.data.IMetaData;
-import com.vladium.emma.report.AbstractReportGenerator;
-import com.vladium.emma.report.AllItem;
-import com.vladium.emma.report.ClassItem;
-import com.vladium.emma.report.IItem;
-import com.vladium.emma.report.IItemAttribute;
-import com.vladium.emma.report.ItemComparator;
-import com.vladium.emma.report.MethodItem;
-import com.vladium.emma.report.PackageItem;
-import com.vladium.emma.report.SourcePathCache;
-import com.vladium.emma.report.SrcFileItem;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class ReportGenerator extends AbstractReportGenerator
-                            implements IAppErrorCodes
-{
-    // public: ................................................................
-    
-    // TODO: this is prototype quality, needs major cleanup
-    
-    // IReportGenerator:
-    
-    public String getType ()
-    {
-        return TYPE;
-    }
-    
-    public void process (final IMetaData mdata, final ICoverageData cdata,
-                         final SourcePathCache cache, final IProperties properties)
-        throws EMMARuntimeException
-    {
-        initialize (mdata, cdata, cache, properties);
-        
-        long start = 0, end;
-        final boolean trace1 = m_log.atTRACE1 ();
-        
-        if (trace1) start = System.currentTimeMillis ();
-        
-        {
-            m_queue = new LinkedList ();
-            for (m_queue.add (m_view.getRoot ()); ! m_queue.isEmpty (); )
-            {
-                final IItem head = (IItem) m_queue.removeFirst ();
-                
-                head.accept (this, null);
-            }
-            line ();
-            
-            close ();
-        }
-                
-        if (trace1)
-        {
-            end = System.currentTimeMillis ();
-            
-            m_log.trace1 ("process", "[" + getType () + "] report generated in " + (end - start) + " ms");
-        }
-    }
-    
-    public void cleanup ()
-    {
-        m_queue = null;
-        close ();
-        
-        super.cleanup ();
-    }
-    
-    
-    // IItemVisitor:
-    
-    public Object visit (final AllItem item, final Object ctx)
-    {
-        File outFile = m_settings.getOutFile ();
-        if (outFile == null)
-        {
-            outFile = new File ("coverage.txt");
-            m_settings.setOutFile (outFile);
-        }
-        
-        final File fullOutFile = Files.newFile (m_settings.getOutDir (), outFile);
-        
-        m_log.info ("writing [" + getType () + "] report to [" + fullOutFile.getAbsolutePath () + "] ...");
-        
-        openOutFile (fullOutFile, m_settings.getOutEncoding (), true);
-        
-        // build ID stamp:
-        try
-        {
-            final StringBuffer label = new StringBuffer (101);
-            
-            label.append ("[");
-            label.append (IAppConstants.APP_NAME);
-            label.append (" v"); label.append (IAppConstants.APP_VERSION_WITH_BUILD_ID_AND_TAG);
-            label.append (" report, generated ");
-            label.append (new Date (EMMAProperties.getTimeStamp ()));
-            label.append ("]");
-            
-            m_out.write (label.toString ());
-            m_out.newLine ();
-            
-            m_out.flush ();
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-        }
-        
-        final int [] columns = m_settings.getColumnOrder ();
-         
-        line ();
-                
-        // [all] coverage summary row:
-        addTitleRow ("OVERALL COVERAGE SUMMARY", 0, 1);            
-        {
-            // header row:
-            addHeaderRow (item, columns);
-            
-            // coverage row:
-            addItemRow (item, columns);
-        }
-                
-        // [all] stats summary table ([all] only):
-        addTitleRow ("OVERALL STATS SUMMARY", 1, 1);
-        {
-            row ("total packages:" + m_separator + item.getChildCount ());
-            row ("total classes:" + m_separator + item.getAggregate (IItem.TOTAL_CLASS_COUNT)); 
-            row ("total methods:" + m_separator + item.getAggregate (IItem.TOTAL_METHOD_COUNT));
-            
-            if (m_srcView && m_hasSrcFileInfo)
-            {
-                row ("total executable files:" + m_separator + item.getAggregate (IItem.TOTAL_SRCFILE_COUNT));
-                
-                if (m_hasLineNumberInfo)
-                    row ("total executable lines:" + m_separator + item.getAggregate (IItem.TOTAL_LINE_COUNT));
-            }
-        }
-        
-        final boolean deeper = (m_settings.getDepth () > item.getMetadata ().getTypeID ());
-        
-        // render package summary rows:
-        addTitleRow ("COVERAGE BREAKDOWN BY PACKAGE", 1, 1);
-        {
-            boolean headerDone = false;
-            final ItemComparator order = m_typeSortComparators [PackageItem.getTypeMetadata ().getTypeID ()];                
-            for (Iterator packages = item.getChildren (order); packages.hasNext (); )
-            {
-                final IItem pkg = (IItem) packages.next ();
-                
-                if (! headerDone)
-                {
-                    // header row:
-                    addHeaderRow (pkg, columns);                        
-                    headerDone = true;
-                }
-                
-                // coverage row:
-                addItemRow (pkg, columns);
-                
-                if (deeper) m_queue.addLast (pkg);
-            }
-        }
-
-        return ctx;
-    }
-    
-    public Object visit (final PackageItem item, final Object ctx)
-    {
-        if (m_verbose) m_log.verbose ("  report: processing package [" + item.getName () + "] ...");
-        
-        final int [] columns = m_settings.getColumnOrder ();
-        
-        line ();
-        
-        // coverage summary row:
-        addTitleRow ("COVERAGE SUMMARY FOR PACKAGE [".concat (item.getName ()).concat ("]"), 0, 1);            
-        {
-            // header row:
-            addHeaderRow (item, columns);
-            
-            // coverage row:
-            addItemRow (item, columns);
-        }
-        
-        
-        final boolean deeper = (m_settings.getDepth () > item.getMetadata ().getTypeID ());
-                
-        // render child summary rows:
-        
-        final String summaryTitle = m_srcView ? "COVERAGE BREAKDOWN BY SOURCE FILE" : "COVERAGE BREAKDOWN BY CLASS";
-        addTitleRow (summaryTitle, 1, 1);
-        {
-            boolean headerDone = false;
-            final ItemComparator order = m_typeSortComparators [m_srcView ? SrcFileItem.getTypeMetadata ().getTypeID () : ClassItem.getTypeMetadata ().getTypeID ()];                
-            for (Iterator srcORclsFiles = item.getChildren (order); srcORclsFiles.hasNext (); )
-            {
-                final IItem srcORcls = (IItem) srcORclsFiles.next ();
-                
-                if (! headerDone)
-                {
-                    // header row:
-                    addHeaderRow (srcORcls, columns);                        
-                    headerDone = true;
-                }
-                
-                // coverage row:
-                addItemRow (srcORcls, columns);
-                
-                if (deeper) m_queue.addLast (srcORcls);
-            }
-        }
-
-        return ctx;
-    }
-
-    public Object visit (final SrcFileItem item, final Object ctx)
-    {
-        final int [] columns = m_settings.getColumnOrder ();
-        
-        line ();
-        
-        // coverage summary row:
-        addTitleRow ("COVERAGE SUMMARY FOR SOURCE FILE [".concat (item.getName ()).concat ("]"), 0, 1);            
-        {
-            // header row:
-            addHeaderRow (item, columns);
-            
-            // coverage row:
-            addItemRow (item, columns);
-        }
-        
-        // render child summary rows:
-        addTitleRow ("COVERAGE BREAKDOWN BY CLASS AND METHOD", 1, 1);
-        {
-            boolean headerDone = false;
-            final ItemComparator order = m_typeSortComparators [ClassItem.getTypeMetadata ().getTypeID ()];                
-            for (Iterator classes = item.getChildren (order); classes.hasNext (); )
-            {
-                final IItem cls = (IItem) classes.next ();
-                
-                if (! headerDone)
-                {
-                    // header row:
-                    addHeaderRow (cls, columns);                        
-                    headerDone = true;
-                }
-                
-                // coverage row:
-                //addItemRow (child, columns);
-                
-                addTitleRow ("class [" + cls.getName () + "] methods", 0, 0);
-                
-                // TODO: select the right comparator here
-                final ItemComparator order2 = m_typeSortComparators [MethodItem.getTypeMetadata ().getTypeID ()];                
-                for (Iterator methods = cls.getChildren (order2); methods.hasNext (); )
-                {
-                    final MethodItem method = (MethodItem) methods.next ();
-                    
-                    addItemRow (method, columns);
-                }
-            }
-        }
-
-        return ctx;
-    }
-    
-    public Object visit (final ClassItem item, final Object ctx)
-    {
-        final int [] columns = m_settings.getColumnOrder ();
-        
-        line ();
-        
-        // coverage summary row:
-        addTitleRow ("COVERAGE SUMMARY FOR CLASS [".concat (item.getName ()).concat ("]"), 0, 1);            
-        {
-            // header row:
-            addHeaderRow (item, columns);
-            
-            // coverage row:
-            addItemRow (item, columns);
-        }
-        
-        // render child summary rows:
-        addTitleRow ("COVERAGE BREAKDOWN BY METHOD", 1, 1);
-        {
-            final ItemComparator order = m_typeSortComparators [MethodItem.getTypeMetadata ().getTypeID ()];                
-            for (Iterator methods = item.getChildren (order); methods.hasNext (); )
-            {
-                final IItem method = (IItem) methods.next ();
-                
-                // coverage row:
-                addItemRow (method, columns);                
-            }
-        }
-
-        return ctx;
-    }
-        
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private void addTitleRow (final String text, final int hlines, final int flines)
-    {
-        for (int i = 0; i < hlines; ++ i) eol ();
-        row (new StringBuffer (text).append (":"));
-        for (int i = 0; i < flines; ++ i) eol ();
-    } 
-    
-    private void addHeaderRow (final IItem item, final int [] columns)
-    {
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (item != null, "null input: item");
-            $assert.ASSERT (columns != null, "null input: columns");
-        }
-        
-        // header row:
-        final StringBuffer buf = new StringBuffer ();
-        
-        for (int c = 0, cLimit = columns.length; c < cLimit; ++ c)
-        {
-            final int attrID = columns [c];
-            final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-            
-            if (attr != null)
-            {
-                buf.append ('[');
-                buf.append (attr.getName ());
-                buf.append (']');
-            }
-            if (c != cLimit - 1) buf.append (m_separator);
-        }
-        
-        row (buf);
-    }
-    
-    
-    /*
-     * No header row, just data rows.
-     */
-    private void addItemRow (final IItem item, final int [] columns)
-    {
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (item != null, "null input: item");
-            $assert.ASSERT (columns != null, "null input: columns");
-        }
-        
-        final StringBuffer buf = new StringBuffer (11); // TODO: reuse a buffer
-        
-        for (int c = 0, cLimit = columns.length; c < cLimit; ++ c)
-        {
-            final int attrID = columns [c];
-            final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-            
-            if (attr != null)
-            {
-                boolean fail = (m_metrics [attrID] > 0) && ! attr.passes (item, m_metrics [attrID]);
-                
-                if (fail)
-                {
-                    //buf.append ('(');
-                    //buf.append ("! ");
-                    attr.format (item, buf);
-                    buf.append ('!');
-                    //buf.append (')');
-                }
-                else
-                {
-                    attr.format (item, buf);
-                }
-            }
-            if (c != cLimit - 1) buf.append (m_separator);
-        }
-        
-        row (buf);
-    }
-    
-    
-    private void row (final StringBuffer str)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (str != null, "str = null");
-        
-        try
-        {
-            m_out.write (str.toString ());
-            m_out.newLine ();
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-        }
-    }
-    
-    private void row (final String str)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (str != null, "str = null");
-        
-        try
-        {
-            m_out.write (str);
-            m_out.newLine ();
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-        }
-    }
-    
-    private void line ()
-    {
-        try
-        {
-            m_out.write (LINE);
-            m_out.newLine ();
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-        }
-    }
-    
-    private void eol ()
-    {
-        try
-        {
-            m_out.newLine ();
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-        }
-    }
-    
-    private void close ()
-    {
-        if (m_out != null)
-        {
-            try
-            {
-                m_out.flush ();
-                m_out.close ();
-            }
-            catch (IOException ioe)
-            {
-                throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-            }
-            finally
-            {
-                m_out = null;
-            }
-        }
-    }
-    
-    private void openOutFile (final File file, final String encoding, final boolean mkdirs)
-    {
-        try
-        {
-            if (mkdirs)
-            {
-                final File parent = file.getParentFile ();
-                if (parent != null) parent.mkdirs ();
-            }
-            
-            m_out = new BufferedWriter (new OutputStreamWriter (new FileOutputStream (file), encoding), IO_BUF_SIZE);
-        }
-        catch (UnsupportedEncodingException uee)
-        {
-            // TODO: error code
-            throw new EMMARuntimeException (uee);
-        }
-        // note: in J2SDK 1.3 FileOutputStream constructor's throws clause
-        // was narrowed to FileNotFoundException:
-        catch (IOException fnfe) // FileNotFoundException
-        {
-            // TODO: error code
-            throw new EMMARuntimeException (fnfe);
-        }
-    }
-    
-    
-    private char m_separator = '\t'; // TODO: set this
-    
-    private LinkedList /* IITem */ m_queue;
-    private BufferedWriter m_out;
-    
-    private static final String TYPE = "txt";
-    private static final String LINE = "-------------------------------------------------------------------------------";
-    
-    private static final int IO_BUF_SIZE = 32 * 1024;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/report/xml/ReportGenerator.java b/core/java12/com/vladium/emma/report/xml/ReportGenerator.java
deleted file mode 100644
index 70be06e..0000000
--- a/core/java12/com/vladium/emma/report/xml/ReportGenerator.java
+++ /dev/null
@@ -1,538 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ReportGenerator.java,v 1.1.1.1.2.1 2004/07/16 23:32:29 vlad_r Exp $
- */
-package com.vladium.emma.report.xml;
-
-import java.io.BufferedWriter;
-import java.io.File;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.OutputStreamWriter;
-import java.io.UnsupportedEncodingException;
-import java.io.Writer;
-import java.util.Date;
-import java.util.Iterator;
-
-import com.vladium.util.Files;
-import com.vladium.util.IConstants;
-import com.vladium.util.IProperties;
-import com.vladium.util.Strings;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMAProperties;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.data.ICoverageData;
-import com.vladium.emma.data.IMetaData;
-import com.vladium.emma.report.AbstractReportGenerator;
-import com.vladium.emma.report.AllItem;
-import com.vladium.emma.report.ClassItem;
-import com.vladium.emma.report.IItem;
-import com.vladium.emma.report.IItemAttribute;
-import com.vladium.emma.report.IItemMetadata;
-import com.vladium.emma.report.ItemComparator;
-import com.vladium.emma.report.MethodItem;
-import com.vladium.emma.report.PackageItem;
-import com.vladium.emma.report.SourcePathCache;
-import com.vladium.emma.report.SrcFileItem;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class ReportGenerator extends AbstractReportGenerator
-                            implements IAppErrorCodes
-{
-    // public: ................................................................
-    
-    // IReportGenerator:
-    
-    public String getType ()
-    {
-        return TYPE;
-    }
-    
-    public void process (final IMetaData mdata, final ICoverageData cdata,
-                         final SourcePathCache cache, final IProperties properties)
-        throws EMMARuntimeException
-    {
-        initialize (mdata, cdata, cache, properties);
-        
-        long start = 0, end;
-        final boolean trace1 = m_log.atTRACE1 ();
-        
-        if (trace1) start = System.currentTimeMillis ();
-        
-        {
-            m_view.getRoot ().accept (this, null);
-            close ();
-        }
-                
-        if (trace1)
-        {
-            end = System.currentTimeMillis ();
-            
-            m_log.trace1 ("process", "[" + getType () + "] report generated in " + (end - start) + " ms");
-        }
-    }
-    
-    public void cleanup ()
-    {
-        close ();
-        
-        super.cleanup ();
-    }
-    
-    
-    // IItemVisitor:
-    
-    public Object visit (final AllItem item, final Object ctx)
-    {
-        try
-        {
-            File outFile = m_settings.getOutFile ();
-            if (outFile == null)
-            {
-                outFile = new File ("coverage.xml");
-                m_settings.setOutFile (outFile);
-            }
-            
-            final File fullOutFile = Files.newFile (m_settings.getOutDir (), outFile);
-            
-            m_log.info ("writing [" + getType () + "] report to [" + fullOutFile.getAbsolutePath () + "] ...");
-            
-            openOutFile (fullOutFile, m_settings.getOutEncoding (), true);
-            
-            // XML header:
-            m_out.write ("<?xml version=\"1.0\" encoding=\"" + m_settings.getOutEncoding () + "\"?>");
-            
-            // build ID stamp:
-            try
-            {
-                final StringBuffer label = new StringBuffer (101);
-                
-                label.append ("<!-- ");
-                label.append (IAppConstants.APP_NAME);
-                label.append (" v"); label.append (IAppConstants.APP_VERSION_WITH_BUILD_ID_AND_TAG);
-                label.append (" report, generated ");
-                label.append (new Date (EMMAProperties.getTimeStamp ()));
-                label.append (" -->");
-                
-                m_out.write (label.toString ());
-                m_out.newLine ();
-                
-                m_out.flush ();
-            }
-            catch (IOException ioe)
-            {
-                throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-            }
-            
-            eol ();
-            openElementTag ("report");
-            closeElementTag (false);
-            m_out.incIndent ();
-            
-            // stats summary section:
-            eol ();
-            openElementTag ("stats");
-            closeElementTag (false);
-            m_out.incIndent ();
-            {
-                emitStatsCount ("packages", item.getChildCount ());
-                emitStatsCount ("classes", item.getAggregate (IItem.TOTAL_CLASS_COUNT));
-                emitStatsCount ("methods", item.getAggregate (IItem.TOTAL_METHOD_COUNT));
-                
-                if (m_srcView && m_hasSrcFileInfo)
-                {
-                    emitStatsCount ("srcfiles", item.getAggregate (IItem.TOTAL_SRCFILE_COUNT));
-                    
-                    if (m_hasLineNumberInfo)
-                        emitStatsCount ("srclines", item.getAggregate (IItem.TOTAL_LINE_COUNT));
-                }
-            }
-            m_out.decIndent ();
-            eol ();
-            endElement ("stats");
-            
-            // actual coverage data:
-            eol ();
-            openElementTag ("data");
-            closeElementTag (false);
-            m_out.incIndent ();
-            {
-                final ItemComparator childrenOrder = m_typeSortComparators [PackageItem.getTypeMetadata ().getTypeID ()];
-                emitItem (item, childrenOrder);
-            }
-            m_out.decIndent ();
-            eol ();
-            endElement ("data");
-            
-            m_out.decIndent ();
-            eol ();
-            endElement ("report");            
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-        }
-
-        return ctx;
-    }
-    
-    
-    public Object visit (final PackageItem item, final Object ctx)
-    {
-        if (m_verbose) m_log.verbose ("  report: processing package [" + item.getName () + "] ...");
-        
-        try
-        {
-            final ItemComparator childrenOrder = m_typeSortComparators [m_srcView ? SrcFileItem.getTypeMetadata ().getTypeID () : ClassItem.getTypeMetadata ().getTypeID ()];
-            emitItem (item, childrenOrder);
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-        }
-
-        return ctx;
-    }
-    
-    
-    public Object visit (final SrcFileItem item, final Object ctx)
-    {
-        try
-        {
-            final ItemComparator childrenOrder = m_typeSortComparators [ClassItem.getTypeMetadata ().getTypeID ()];
-            emitItem (item, childrenOrder);
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-        }
-
-        return ctx;
-    }
-
-    public Object visit (final ClassItem item, final Object ctx)
-    {
-        try
-        {
-            final ItemComparator childrenOrder = m_typeSortComparators [MethodItem.getTypeMetadata ().getTypeID ()];
-            emitItem (item, childrenOrder);
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-        }
-
-        return ctx;
-    }
-    
-    public Object visit (final MethodItem item, final Object ctx)
-    {
-        try
-        {
-            emitItem (item, null);
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-        }
-
-        return ctx;
-    }
-        
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final class IndentingWriter extends BufferedWriter
-    {
-        public void newLine () throws IOException
-        {
-            m_state = 0;
-            super.write (IConstants.EOL, 0, IConstants.EOL.length ());
-        }
-                
-        public void write (final char [] cbuf, final int off, final int len) throws IOException
-        {
-            indent ();
-            super.write (cbuf, off, len);
-        }
-
-        public void write (int c) throws IOException
-        {
-            indent ();
-            super.write (c);
-        }
-
-        public void write (final String s, final int off, final int len) throws IOException
-        {
-            indent ();
-            super.write (s, off, len);
-        }
-
-        
-        IndentingWriter (final Writer out, final int buffer, final int indent)
-        {
-            super (out, buffer);
-            m_indent = indent;
-        }
-
-        
-        void incIndent (final int delta)
-        {
-            if (delta < 0) throw new IllegalArgumentException ("delta be non-negative: " + delta);
-            
-            m_indent += delta;
-        }
-        
-        void incIndent ()
-        {
-            incIndent (INDENT_INCREMENT);
-        }
-        
-        void decIndent (final int delta)
-        {
-            if (delta < 0) throw new IllegalArgumentException ("delta be non-negative: " + delta);
-            if (delta > m_indent) throw new IllegalArgumentException ("delta = " + delta + ", current indent = " + m_indent);
-            
-            m_indent -= delta;
-        }
-        
-        void decIndent ()
-        {
-            decIndent (INDENT_INCREMENT);
-        }
-        
-        String getIndent ()
-        {
-            if (m_indent <= 0)
-                return "";
-            else
-            {
-                if ((m_sindent == null) || (m_sindent.length () < m_indent))
-                {
-                    final char [] ca = new char [m_indent];
-                    
-                    for (int i = 0; i < m_indent; ++ i) ca [i] = ' ';
-                    m_sindent = new String (ca);
-                    
-                    return m_sindent;
-                }
-                else
-                {
-                    return m_sindent.substring (0, m_indent);
-                }
-            }
-        }
-        
-                
-        private void indent ()
-            throws IOException
-        {
-            if (m_state == 0)
-            {
-                final String indent = getIndent ();
-                super.write (indent, 0, indent.length ());
-                
-                m_state = 1;
-            }
-        }
-        
-        
-        private int m_indent;
-        private int m_state;
-        private transient String m_sindent;
-        
-        private static final int INDENT_INCREMENT = 2;
-        
-    } // end of nested class
-    
-    
-    private void emitStatsCount (final String name, final int value)
-        throws IOException
-    {
-        eol ();
-        openElementTag (name);
-        m_out.write (" value=\"" + value);
-        m_out.write ('"');
-        closeElementTag (true);
-    } 
-
-    private void emitItem (final IItem item, final ItemComparator childrenOrder)
-        throws IOException
-    {        
-        final IItemMetadata metadata = item.getMetadata (); 
-        final int [] columns = m_settings.getColumnOrder ();            
-        final String tag = metadata.getTypeName ();
- 
-        eol ();
-        
-        // emit opening tag with name attribute:
-        {
-            openElementTag (tag);
-            
-            m_out.write (" name=\"");
-            m_out.write (Strings.HTMLEscape (item.getName ()));
-            m_out.write ('"');
-            
-            closeElementTag (false);
-        }
-        
-        eol ();
-            
-        m_out.incIndent ();       
-
-        emitItemCoverage (item, columns);
-        
-        final boolean deeper = (childrenOrder != null) && (m_settings.getDepth () > metadata.getTypeID ()) && (item.getChildCount () > 0);
-        
-        if (deeper)
-        {
-            for (Iterator packages = item.getChildren (childrenOrder); packages.hasNext (); )
-            {
-                ((IItem) packages.next ()).accept (this, null);
-            }
-            
-            eol ();
-        }
-
-        m_out.decIndent ();
-        
-        // emit closing tag:
-        {
-            endElement (tag);
-        }
-    }
-    
-    /*
-     * No header row, just data rows.
-     */
-    private void emitItemCoverage (final IItem item, final int [] columns)
-        throws IOException
-    {
-        final StringBuffer buf = new StringBuffer (64);
-        
-        for (int c = 0, cLimit = columns.length; c < cLimit; ++ c)
-        {
-            final int attrID = columns [c];
-            
-            if (attrID != IItemAttribute.ATTRIBUTE_NAME_ID)
-            {
-                final IItemAttribute attr = item.getAttribute (attrID, m_settings.getUnitsType ());
-                
-                if (attr != null)
-                {
-                    openElementTag ("coverage");
-
-                    m_out.write (" type=\"");
-                    m_out.write (Strings.HTMLEscape (attr.getName ()));
-                    m_out.write ("\" value=\"");
-                    attr.format (item, buf);
-                    m_out.write (Strings.HTMLEscape (buf.toString ()));
-                    m_out.write ('"');
-                    buf.setLength (0);
-                    
-                    closeElementTag (true);
-                    
-                    eol ();
-                }
-            }
-        }
-        
-    }
-    
-    private void openElementTag (final String tag)
-        throws IOException
-    {
-        m_out.write ('<');
-        m_out.write (tag);
-    }
-    
-    private void closeElementTag (final boolean simple)
-        throws IOException
-    {
-        if (simple)
-            m_out.write ("/>");
-        else
-            m_out.write ('>');
-    }
-    
-    private void endElement (final String tag)
-        throws IOException
-    {
-        m_out.write ("</");
-        m_out.write (tag);
-        m_out.write ('>');
-    }
-    
-    private void eol ()
-        throws IOException
-    {
-        m_out.newLine ();
-    }
-    
-    private void close ()
-    {
-        if (m_out != null)
-        {
-            try
-            {
-                m_out.flush ();
-                m_out.close ();
-            }
-            catch (IOException ioe)
-            {
-                throw new EMMARuntimeException (IAppErrorCodes.REPORT_IO_FAILURE, ioe);
-            }
-            finally
-            {
-                m_out = null;
-            }
-        }
-    }
-    
-    private void openOutFile (final File file, final String encoding, final boolean mkdirs)
-    {
-        try
-        {
-            if (mkdirs)
-            {
-                final File parent = file.getParentFile ();
-                if (parent != null) parent.mkdirs ();
-            }
-            
-            m_out = new IndentingWriter (new OutputStreamWriter (new FileOutputStream (file), encoding), IO_BUF_SIZE, 0);
-        }
-        catch (UnsupportedEncodingException uee)
-        {
-            // TODO: error code
-            throw new EMMARuntimeException (uee);
-        }
-        // note: in J2SDK 1.3 FileOutputStream constructor's throws clause
-        // was narrowed to FileNotFoundException:
-        catch (IOException fnfe) // FileNotFoundException
-        {
-            // TODO: error code
-            throw new EMMARuntimeException (fnfe);
-        }
-    }
-    
-    
-    private IndentingWriter m_out;
-    
-    private static final String TYPE = "xml";    
-    private static final int IO_BUF_SIZE = 64 * 1024;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/rt/AppRunner.java b/core/java12/com/vladium/emma/rt/AppRunner.java
deleted file mode 100644
index ad9fd1f..0000000
--- a/core/java12/com/vladium/emma/rt/AppRunner.java
+++ /dev/null
@@ -1,964 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AppRunner.java,v 1.1.1.1.2.2 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma.rt;
-
-import java.io.File;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-import java.net.MalformedURLException;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.ArrayList;
-import java.util.List;
-import java.util.Map;
-
-import com.vladium.logging.Logger;
-import com.vladium.util.Files;
-import com.vladium.util.IConstants;
-import com.vladium.util.IProperties;
-import com.vladium.util.Property;
-import com.vladium.util.SoftValueMap;
-import com.vladium.util.Strings;
-import com.vladium.util.asserts.$assert;
-import com.vladium.util.exception.Exceptions;
-import com.vladium.util.exit.ExitHookManager;
-import com.vladium.emma.AppLoggers;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMAProperties;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.Processor;
-import com.vladium.emma.filter.IInclExclFilter;
-import com.vladium.emma.data.CoverageOptionsFactory;
-import com.vladium.emma.data.IMetaData;
-import com.vladium.emma.data.ICoverageData;
-import com.vladium.emma.data.DataFactory;
-import com.vladium.emma.data.ISessionData;
-import com.vladium.emma.data.SessionData;
-import com.vladium.emma.report.AbstractReportGenerator;
-import com.vladium.emma.report.IReportGenerator;
-import com.vladium.emma.report.SourcePathCache;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class AppRunner extends Processor
-                      implements IAppErrorCodes
-{
-    // public: ................................................................
-    
-    
-    public static AppRunner create (final ClassLoader delegate)
-    {
-        return new AppRunner (delegate);
-    }
-    
-    
-    public synchronized void run ()
-    {
-        validateState ();
-        
-        // disable Runtime's own exit hook:
-        RTSettings.setStandaloneMode (false); // an optimization to disable RT's static init code [this line must precede any reference to RT]
-        RT.reset (true, false); // reset RT [RT creates 'cdata' and loads app properties]
-
-        // load tool properties:
-        final IProperties toolProperties;
-        {
-            IProperties appProperties = RT.getAppProperties (); // try to use app props consistent with RT's view of them
-            if (appProperties == null) appProperties = EMMAProperties.getAppProperties (); // don't use combine()
-            
-            toolProperties = IProperties.Factory.combine (m_propertyOverrides, appProperties);
-        }
-        if ($assert.ENABLED) $assert.ASSERT (toolProperties != null, "toolProperties is null"); // can be empty, though
-
-        final Logger current = Logger.getLogger ();
-        final Logger log = AppLoggers.create (m_appName, toolProperties, current);
-        
-        if (log.atTRACE1 ())
-        {
-            log.trace1 ("run", "complete tool properties:");
-            toolProperties.list (log.getWriter ());
-        }
-        
-        try
-        {
-            Logger.push (log);
-            m_log = log;
-        
-            _run (toolProperties);
-        }
-        finally
-        {
-            if (m_log != null)
-            {
-                Logger.pop (m_log);
-                m_log = null;
-            }
-        }
-    }
-    
-
-    /**
-     * @param path [null is equivalent to empty array]
-     * @param canonical
-     */
-    public synchronized void setCoveragePath (String [] path, final boolean canonical)
-    {
-        if ((path == null) || (path.length == 0))
-            m_coveragePath = IConstants.EMPTY_FILE_ARRAY;
-        else
-            m_coveragePath = Files.pathToFiles (path, canonical);
-        
-        m_canonical = canonical;
-    }
-    
-    public synchronized void setScanCoveragePath (final boolean scan)
-    {
-        m_scanCoveragePath = scan;
-    }
-    
-    /**
-     * @param path [null is equivalent to no source path]
-     */
-    public synchronized void setSourcePath (final String [] path)
-    {
-        if (path == null)
-            m_sourcePath = null;
-        else
-            m_sourcePath = Files.pathToFiles (path, true); // always canonicalize source path
-    }
-
-    /**
-     * 
-     * @param specs [null is equivalent to no filtering (everything is included)]
-     */    
-    public synchronized final void setInclExclFilter (final String [] specs)
-    {
-        if (specs == null)
-            m_coverageFilter = null;
-        else
-            m_coverageFilter = IInclExclFilter.Factory.create (specs);
-    }
-    
-    /**
-     * 
-     * @param className [may not be null or empty]
-     * @param args [null is equivalent to an empty array]
-     */
-    public synchronized void setAppClass (final String className, final String [] args)
-    {
-        if ((className == null) || (className.length () == 0))
-            throw new IllegalArgumentException ("null/empty input: className");
-        
-        if (args != null)
-        {
-            final String [] _args = (String []) args.clone ();
-             
-            for (int a = 0; a < _args.length; ++ a)
-                if (_args [a] == null) throw new IllegalArgumentException ("null input: args[" + a + "]");
-                
-            m_appArgs = _args;
-        }
-        else
-        {
-            m_appArgs = IConstants.EMPTY_STRING_ARRAY;
-        }
-        
-        m_appClassName = className;
-    }
-    
-    public synchronized void setDumpSessionData (final boolean dump)
-    {
-        m_dumpSessionData = dump;    
-    }
-    
-    /**
-     * 
-     * @param fileName [null unsets the previous override setting]
-     */
-    public synchronized final void setSessionOutFile (final String fileName)
-    {
-        if (fileName == null)
-            m_sdataOutFile = null;
-        else
-        {
-            final File _file = new File (fileName);
-                
-            if (_file.exists () && ! _file.isFile ())
-                throw new IllegalArgumentException ("not a file: [" + _file.getAbsolutePath () + "]");
-                
-            m_sdataOutFile = _file;
-        }
-    }
-    
-    /**
-     * 
-     * @param merge [null unsets the previous override setting]
-     */
-    public synchronized final void setSessionOutMerge (final Boolean merge)
-    {
-        m_sdataOutMerge = merge;
-    }
-    
-    /**
-     * 
-     * @param types [may not be null]
-     */
-    public synchronized void setReportTypes (final String [] types)
-    {
-        if (types == null) throw new IllegalArgumentException ("null input: types");
-        
-        final String [] reportTypes = Strings.removeDuplicates (types, true);
-        if (reportTypes.length == 0) throw new IllegalArgumentException ("empty input: types");
-        
-        if ($assert.ENABLED) $assert.ASSERT (reportTypes != null && reportTypes.length  > 0);
-        
-        
-        final IReportGenerator [] reportGenerators = new IReportGenerator [reportTypes.length];
-        for (int t = 0; t < reportTypes.length; ++ t)
-        {
-            reportGenerators [t] = AbstractReportGenerator.create (reportTypes [t]);
-        }
-        
-        m_reportGenerators = reportGenerators;
-    }
-
-    // protected: .............................................................
-
-
-    protected void validateState ()
-    {
-        super.validateState ();
-        
-        if ((m_appClassName == null) || (m_appClassName.length () == 0))
-            throw new IllegalStateException ("application class name not set");
-        
-        if (m_appArgs == null)
-            throw new IllegalStateException ("application arguments not set");
-
-        if (m_coveragePath == null)
-            throw new IllegalStateException ("coverage path not set");
-        
-        // [m_coverageFilter can be null]
-        
-        // [m_sdataOutFile can be null]
-        // [m_sdataOutMerge can be null]
-        
-        if ((m_reportGenerators == null) || (m_reportGenerators.length == 0))
-            throw new IllegalStateException ("report types not set");
-
-        // [m_sourcePath can be null/empty]
-        
-        // [m_propertyOverrides can be null]
-    }
-    
-    
-    protected void _run (final IProperties toolProperties)
-    {
-        final Logger log = m_log;
-        
-        final boolean verbose = log.atVERBOSE ();
-        if (verbose)
-        {
-            log.verbose (IAppConstants.APP_VERBOSE_BUILD_ID);
-            
-            // [assertion: m_coveragePath != null]
-            log.verbose ("coverage path:");
-            log.verbose ("{");
-            for (int p = 0; p < m_coveragePath.length; ++ p)
-            {
-                final File f = m_coveragePath [p];
-                final String nonexistent = f.exists () ? "" : "{nonexistent} ";
-                
-                log.verbose ("  " + nonexistent + f.getAbsolutePath ());
-            }
-            log.verbose ("}");
-            
-            if ((m_sourcePath == null) || (m_sourcePath.length == 0))
-            {
-                log.verbose ("source path not set");
-            }
-            else
-            {
-                log.verbose ("source path:");
-                log.verbose ("{");
-                for (int p = 0; p < m_sourcePath.length; ++ p)
-                {
-                    final File f = m_sourcePath [p];
-                    final String nonexistent = f.exists () ? "" : "{nonexistent} ";
-                    
-                    log.verbose ("  " + nonexistent + f.getAbsolutePath ());
-                }
-                log.verbose ("}");
-            }
-        }
-        
-        // get the data out settings [note: this is not conditioned on m_dumpRawData]:
-        File sdataOutFile = m_sdataOutFile;
-        Boolean sdataOutMerge = m_sdataOutMerge;
-        {
-            if (sdataOutFile == null)
-                sdataOutFile = new File (toolProperties.getProperty (EMMAProperties.PROPERTY_SESSION_DATA_OUT_FILE,
-                                                                     EMMAProperties.DEFAULT_SESSION_DATA_OUT_FILE));
-            
-            if (sdataOutMerge == null)
-            {
-                final String _dataOutMerge = toolProperties.getProperty (EMMAProperties.PROPERTY_SESSION_DATA_OUT_MERGE,
-                                                                         EMMAProperties.DEFAULT_SESSION_DATA_OUT_MERGE.toString ());
-                sdataOutMerge = Property.toBoolean (_dataOutMerge) ? Boolean.TRUE : Boolean.FALSE;
-            } 
-        }
-        
-        if (verbose && m_dumpSessionData)
-        {
-            log.verbose ("session data output file: " + sdataOutFile.getAbsolutePath ());
-            log.verbose ("session data output merge mode: " + sdataOutMerge);
-        }
-        
-        // get instr class loader delegation filter settings:
-        final IInclExclFilter forcedDelegationFilter
-            = IInclExclFilter.Factory.create (toolProperties.getProperty (InstrClassLoader.PROPERTY_FORCED_DELEGATION_FILTER),
-                                              COMMA_DELIMITERS, FORCED_DELEGATION_FILTER_SPECS);
-        final IInclExclFilter throughDelegationFilter
-            = IInclExclFilter.Factory.create (toolProperties.getProperty (InstrClassLoader.PROPERTY_THROUGH_DELEGATION_FILTER),
-                                              COMMA_DELIMITERS, null);
-        
-
-        // TODO: consider injecting Runtime straight into appLoader namespace...
-        // TODO: create a thread group for all exit hooks?
-
-
-        // get a handle to exit hook manager singleton:
-        ExitHookManager runnerExitHookManager = null;
-        try
-        {
-            runnerExitHookManager = ExitHookManager.getSingleton (); // can throw
-        }
-        catch (Exception e)
-        {
-            // TODO: log/handle/warn
-            e.printStackTrace (System.out);
-        }
-
-        AppRunnerExitHook runnerExitHook = null;
-        RuntimeException failure = null;
-        
-        try
-        { 
-            SourcePathCache srcpathCache = null;
-            if (m_sourcePath != null) srcpathCache = new SourcePathCache (m_sourcePath, true); // ignore non-existent source dirs
-            
-            // create session data containers:
-            ICoverageData cdata = RT.getCoverageData ();
-            if ($assert.ENABLED) $assert.ASSERT (cdata != null, "cdata is null");
-            
-            IMetaData mdata = DataFactory.newMetaData (CoverageOptionsFactory.create (toolProperties));
-            
-            runnerExitHook = new AppRunnerExitHook (log, m_dumpSessionData, sdataOutFile, sdataOutMerge.booleanValue (), mdata, cdata, m_reportGenerators, srcpathCache, toolProperties);
-            
-            if (runnerExitHookManager != null)
-                runnerExitHookManager.addExitHook (runnerExitHook);
-            
-            // --------------[ start of exit hook-protected section ]--------------
-            
-            Map classIOCache = null;
-            
-            // scan the classpath to populate the initial metadata:
-            if (m_scanCoveragePath)
-            {
-                if (USE_SOFT_CACHE)
-                    classIOCache = new SoftValueMap (INIT_CACHE_CAPACITY, 0.75F, SOFT_CACHE_READ_CHK_FREQUENCY, SOFT_CACHE_WRITE_CHK_FREQUENCY);
-                else
-                    classIOCache = new HashMap (INIT_CACHE_CAPACITY, 0.75F);
-                    
-                final ClassPathProcessorST processor = new ClassPathProcessorST (m_coveragePath, m_canonical, mdata, m_coverageFilter, classIOCache);
-                
-                // with a bit of work [ClassPathProcessorST needs to lock on the
-                // metadata, etc] this could be run concurrently with the app
-                // itself to improve perceived performance, however, I am not
-                // going to invest time in this; 
-                
-                // populate 'cache' [optional] and 'mdata':
-                processor.run ();
-                
-                if (log.atTRACE1 ())
-                {
-                    log.trace1 ("run", "class cache size after cp scan: " + classIOCache.size ());
-                    log.trace1 ("run", "metadata size after cp scan: " + mdata.size ());
-                }
-            }
-            
-            
-            // app runner does not need these handles anymore [only the exit hook runner maintains them]:
-            srcpathCache = null;
-            cdata = null;
-            
-            final ClassLoader appLoader;
-            {
-                final IClassLoadHook loadHook = new InstrClassLoadHook (m_coverageFilter, mdata);
-                 
-                try
-                {
-                    appLoader = new InstrClassLoader (m_delegate, m_coveragePath, forcedDelegationFilter, throughDelegationFilter, loadHook, classIOCache);
-                }
-                catch (SecurityException se)
-                {
-                    throw new EMMARuntimeException (SECURITY_RESTRICTION, new String [] {IAppConstants.APP_NAME}, se);
-                }
-                catch (MalformedURLException mue)
-                {
-                    throw new EMMARuntimeException (mue); 
-                }
-            }
-            
-            // app runner does not need these handles anymore:
-            mdata = null;
-            classIOCache = null;
-
-            
-            final ClassLoader contextLoader;
-            boolean contextLoaderSet = false;
-            if (SET_CURRENT_CONTEXT_LOADER)
-            {
-                try
-                {
-                    final Thread currentThread = Thread.currentThread (); 
-                    
-                    // TODO: rethink if this is the right place to do this
-                    contextLoader = currentThread.getContextClassLoader ();
-                    currentThread.setContextClassLoader (appLoader);
-                    
-                    contextLoaderSet = true;
-                }
-                catch (SecurityException se)
-                {
-                    throw new EMMARuntimeException (SECURITY_RESTRICTION, new String [] {IAppConstants.APP_NAME}, se);
-                }
-            }
-            
-            
-            ThreadGroup appThreadGroup = null;
-            try
-            {
-                // load [and possibly initialize] the app class:
-                
-                final Class appClass;
-                try
-                {
-                    // load [and force early initialization if INIT_AT_LOAD_TIME is 'true']:
-                    appClass = Class.forName (m_appClassName, INIT_AT_LOAD_TIME, appLoader);
-                }
-                catch (ClassNotFoundException cnfe)
-                {
-                    // TODO: dump the classloader tree into the error message as well
-                    throw new EMMARuntimeException (MAIN_CLASS_NOT_FOUND, new String [] {m_appClassName}, cnfe);
-                }
-                catch (ExceptionInInitializerError eiie) // this should not happen for INIT_AT_LOAD_TIME=false
-                {
-                    final Throwable cause = eiie.getException ();
-                    
-                    throw new EMMARuntimeException (MAIN_CLASS_LOAD_FAILURE, new String [] {m_appClassName, cause.toString ()}, cause);
-                }
-                catch (Throwable t)
-                {
-                    throw new EMMARuntimeException (MAIN_CLASS_NOT_FOUND, new String [] {m_appClassName}, t);
-                }
-                
-                // ensure that the app is bootstrapped using appLoader:
-                {
-                    final ClassLoader actualLoader = appClass.getClassLoader ();
-                    if (actualLoader != appLoader)
-                    {
-                        final String loaderName = actualLoader != null ?  actualLoader.getClass ().getName () : "<PRIMORDIAL>";
-                        
-                        throw new EMMARuntimeException (MAIN_CLASS_BAD_DELEGATION, new String [] {IAppConstants.APP_NAME, m_appClassName, loaderName});
-                    }
-                }
-    
-                // run the app's main():
-                
-                final Method appMain;
-                try
-                {
-                    // this causes initialization on some non-Sun-compatible JVMs [ignore]:
-                    appMain = appClass.getMethod ("main", MAIN_TYPE); // Sun JVMs do not seem to require the method to be declared
-                }
-                catch (Throwable t)
-                {
-                    throw new EMMARuntimeException (MAIN_METHOD_NOT_FOUND, new String [] {m_appClassName}, t);
-                }            
-                
-                Invoker invoker = new Invoker (appMain, null, new Object [] {m_appArgs});
-                
-                appThreadGroup = new ThreadGroup (IAppConstants.APP_NAME + " thread group [" + m_appClassName + "]");
-                appThreadGroup.setDaemon (true);
-                
-                Thread appThread = new Thread (appThreadGroup, invoker, IAppConstants.APP_NAME + " main() thread");
-                appThread.setContextClassLoader (appLoader);
-                
-                // --- [app start] ----
-                
-                appThread.start ();
-                
-                try {appThread.join (); } catch (InterruptedException ignore) {}
-                appThread = null;
-                
-                joinNonDeamonThreads (appThreadGroup);
-                
-                // --- [app end] ----
-                
-                if (log.atTRACE1 ())
-                {
-                    if (appLoader instanceof InstrClassLoader) ((InstrClassLoader) appLoader).debugDump (log.getWriter ());
-                }
-                
-                final Throwable mainFailure = invoker.getFailure ();
-                invoker = null;
-                
-                if (mainFailure != null)
-                {
-                    if (mainFailure instanceof InvocationTargetException)
-                    {
-                        final Throwable cause = ((InvocationTargetException) mainFailure).getTargetException ();
-                        
-                        throw new EMMARuntimeException (MAIN_METHOD_FAILURE, new String [] {m_appClassName, cause.toString ()}, cause);
-                    }
-                    else if (mainFailure instanceof ExceptionInInitializerError)
-                    {
-                        // this catch block is never entered if INIT_AT_LOAD_TIME is 'true'
-                        final Throwable cause = ((ExceptionInInitializerError) mainFailure).getException ();
-                        
-                        throw new EMMARuntimeException (MAIN_METHOD_FAILURE, new String [] {m_appClassName, cause.toString ()}, cause);
-                    }
-                    else if ((mainFailure instanceof IllegalAccessException)   ||
-                             (mainFailure instanceof IllegalArgumentException) ||
-                             (mainFailure instanceof NullPointerException))
-                    {
-                        throw new EMMARuntimeException (MAIN_METHOD_NOT_FOUND, new String [] {m_appClassName}, mainFailure);
-                    }
-                    else
-                    {
-                        throw new EMMARuntimeException (MAIN_METHOD_FAILURE, new String [] {m_appClassName, mainFailure.toString ()}, mainFailure);
-                    }
-                }                
-            }
-            catch (SecurityException se)
-            {
-                throw new EMMARuntimeException (SECURITY_RESTRICTION, new String [] {IAppConstants.APP_NAME}, se);
-            }
-            finally
-            {
-                if (SET_CURRENT_CONTEXT_LOADER && contextLoaderSet)
-                {
-                    try
-                    {
-                        Thread.currentThread ().setContextClassLoader (contextLoader);
-                    }
-                    catch (Throwable ignore) {} 
-                }
-
-                if ((appThreadGroup != null) && ! appThreadGroup.isDestroyed ())
-                try
-                {
-                    appThreadGroup.destroy ();
-                    appThreadGroup = null;
-                }
-                catch (Throwable ignore) {}                
-            }
-        }
-        catch (RuntimeException re)
-        {
-            failure = re; // should be EMMARuntimeException only if there are no errors above
-        }
-        finally
-        {
-            RT.reset (false, false);
-        }
-        
-        if ($assert.ENABLED) $assert.ASSERT (runnerExitHook != null, "reportExitHook = null");
-        runnerExitHook.run (); // that this may be a noop (if the shutdown sequence got there first)
-        
-        // [assertion: the report exit hook is done]
-                
-        if (runnerExitHookManager != null)
-        {
-            runnerExitHookManager.removeExitHook (runnerExitHook); // Ok if this fails
-            runnerExitHookManager = null;
-        }
-        
-        // ---------------[ end of exit hook-protected section ]---------------
-        
-        
-        final Throwable exitHookDataDumpFailure = runnerExitHook.getDataDumpFailure ();
-        final List /* Throwable */ exitHookReportFailures = runnerExitHook.getReportFailures ();
-        runnerExitHook = null;        
-        
-        if (failure != null) // 'failure' takes precedence over any possible exit hook's problems
-        {
-            throw wrapFailure (failure);
-        }
-        else if ((exitHookDataDumpFailure != null) || (exitHookReportFailures != null))
-        {
-            if (exitHookDataDumpFailure != null)
-                log.log (Logger.SEVERE, "exception while persisting raw session data:", exitHookDataDumpFailure);
-            
-            Throwable firstReportFailure = null;
-            if (exitHookReportFailures != null)
-            {
-                for (Iterator i = exitHookReportFailures.iterator (); i.hasNext (); )
-                {
-                    final Throwable reportFailure = (Throwable) i.next ();                
-                    if (firstReportFailure == null) firstReportFailure = reportFailure;
-                    
-                    log.log (Logger.SEVERE, "exception while creating a report:", reportFailure);
-                }
-            }
-            
-            if (exitHookDataDumpFailure != null)
-                throw wrapFailure (exitHookDataDumpFailure);
-            else if (firstReportFailure != null) // redundant check
-                throw wrapFailure (firstReportFailure);
-        }
-
-    }
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final class Invoker implements Runnable
-    {
-        Invoker (final Method method, final Object target, final Object [] args)
-        {
-            if (method == null) throw new IllegalArgumentException ("null input: method");
-            if (args == null) throw new IllegalArgumentException ("null input: args");
-            
-            m_method = method;
-            m_target = target;
-            m_args = args;
-        }
-        
-        public void run ()
-        {
-            try
-            {
-                m_method.invoke (m_target, m_args);
-            }
-            catch (Throwable t)
-            {
-                m_failure = t;
-            }
-        }
-        
-        Throwable getFailure ()
-        {
-            return m_failure;
-        }
-        
-        
-        private final Method m_method;
-        private final Object m_target;
-        private final Object [] m_args;
-        private Throwable m_failure;
-        
-    } // end of nested class
-    
-    
-    private static final class AppRunnerExitHook implements Runnable
-    {
-        public synchronized void run ()
-        {
-            try
-            {
-                if (! m_done)
-                {
-                    // grab data snapshots:
-                    
-                    final IMetaData mdataSnashot = m_mdata.shallowCopy ();
-                    m_mdata = null;
-                    final ICoverageData cdataSnapshot = m_cdata.shallowCopy ();
-                    m_cdata = null;
-                    
-                    if (mdataSnashot.isEmpty ())
-                    {
-                        m_log.warning ("no metadata collected at runtime [no reports generated]");
-                        
-                        return;
-                    }
-                    
-                    if (cdataSnapshot.isEmpty ())
-                    {
-                        m_log.warning ("no coverage data collected at runtime [all reports will be empty]");
-                    }
-                    
-                    final ISessionData sdata = new SessionData (mdataSnashot, cdataSnapshot);
-
-                    // if requested, dump raw data before running report generators:                    
-                    // [note that the raw dumps and reports will be consistent wrt
-                    // the session data they represent]
-                    
-                    if (m_dumpRawData && (m_sdataOutFile != null))
-                    {
-                       try
-                        {
-                            final boolean info = m_log.atINFO ();
-                            
-                            final long start = info ? System.currentTimeMillis () : 0;
-                            {
-                                DataFactory.persist (sdata, m_sdataOutFile, m_sdataOutMerge);
-                            }
-                            if (info)
-                            {
-                                final long end = System.currentTimeMillis ();
-                                
-                                m_log.info ("raw session data " + (m_sdataOutMerge ? "merged into" : "written to") + " [" + m_sdataOutFile.getAbsolutePath () + "] {in " + (end - start) + " ms}");
-                            }
-                        }
-                        catch (Throwable t)
-                        {
-                            m_dataDumpFailure = t;
-                        }
-                    }
-                    
-                    for (int g = 0; g < m_generators.length; ++ g)
-                    {
-                        final IReportGenerator generator = m_generators [g];
-                        
-                        if (generator != null)
-                        {
-                            try
-                            {
-                                generator.process (mdataSnashot, cdataSnapshot, m_cache, m_properties);
-                            }
-                            catch (Throwable t)
-                            {
-                                if (m_reportFailures == null) m_reportFailures = new ArrayList ();
-                                m_reportFailures.add (t);
-                                
-                                continue;
-                            }
-                            finally
-                            {
-                                try { generator.cleanup (); } catch (Throwable ignore) {}
-                                m_generators [g] = null;
-                            }
-                        }
-                    }                    
-                }
-            }
-            finally
-            {
-                m_generators = null;
-                m_mdata = null;
-                m_cdata = null;
-                m_properties = null;
-                m_cache = null;
-                
-                m_done = true;
-            }
-        }
-        
-        // note: because ExitHookManager is a lazily created static singleton the
-        // correct thing to do is to pass an explicit Logger into each exit hook runner
-        // instead of relying on thread inheritance:
-        
-        AppRunnerExitHook (final Logger log,
-                           final boolean dumpRawData, final File sdataOutFile, final boolean sdataOutMerge,
-                           final IMetaData mdata, final ICoverageData cdata,
-                           final IReportGenerator [] generators,
-                           final SourcePathCache cache, final IProperties properties)
-        {
-            if (log == null) throw new IllegalArgumentException ("null input: log");
-            if ((generators == null) || (generators.length == 0)) throw new IllegalArgumentException ("null/empty input: generators");
-            if (mdata == null) throw new IllegalArgumentException ("null input: mdata");
-            if (cdata == null) throw new IllegalArgumentException ("null input: cdata");
-            if (properties == null) throw new IllegalArgumentException ("null input: properties");
-            
-            m_log = log;
-            
-            m_dumpRawData = dumpRawData;
-            m_sdataOutFile = sdataOutFile;
-            m_sdataOutMerge = sdataOutMerge;
-            
-            m_generators = (IReportGenerator []) generators.clone ();
-            m_mdata = mdata;
-            m_cdata = cdata;
-            m_cache = cache;
-            m_properties = properties;
-        }
-
-        
-        synchronized Throwable getDataDumpFailure ()
-        {
-            return m_dataDumpFailure;
-        }
-        
-        synchronized List /* Throwable */ getReportFailures ()
-        {
-            return m_reportFailures;
-        }
-
-
-        private final Logger m_log;
-        private final boolean m_dumpRawData;
-        private final File m_sdataOutFile;
-        private final boolean m_sdataOutMerge;
-        
-        private IReportGenerator [] m_generators;
-        private IMetaData m_mdata;
-        private ICoverageData m_cdata;
-        private SourcePathCache m_cache;
-        private IProperties m_properties;
-        private boolean m_done;
-        private Throwable m_dataDumpFailure;
-        private List /* Throwable */ m_reportFailures;
-        
-    } // end of nested class 
-    
-    
-    private AppRunner (final ClassLoader delegate)
-    {
-        m_delegate = delegate;
-        m_coveragePath = IConstants.EMPTY_FILE_ARRAY;
-    }
-    
-    
-    private static void joinNonDeamonThreads (final ThreadGroup group)
-    {
-        if (group == null) throw new IllegalArgumentException ("null input: group");
-        
-        final List threads = new ArrayList ();
-        while (true)
-        {
-            threads.clear ();
-            
-            // note: group.activeCount() is only an estimate as more threads
-            // could get created while we are doing this [if 'aliveThreads'
-            // array is too short, the extra threads are silently ignored]:
-            
-            Thread [] aliveThreads;
-            final int aliveCount;
-            
-            // enumerate [recursively] all threads in 'group':
-            synchronized (group)
-            {
-                aliveThreads = new Thread [group.activeCount () << 1];
-                aliveCount = group.enumerate (aliveThreads, true);
-            }
-            
-            for (int t = 0; t < aliveCount; t++)
-            {
-                if (! aliveThreads [t].isDaemon ())
-                    threads.add (aliveThreads [t]);
-            }            
-            aliveThreads = null;
-            
-            if (threads.isEmpty ())
-                break; // note: this logic does not work if daemon threads are spawning non-daemon ones
-            else
-            {
-                for (Iterator i = threads.iterator (); i.hasNext (); )
-                {
-                    try
-                    {
-                        ((Thread) i.next ()).join (); 
-                    }
-                    catch (InterruptedException ignore) {}
-                }
-            }
-        }
-    }
-    
-    private static RuntimeException wrapFailure (final Throwable t)
-    {
-        if (Exceptions.unexpectedFailure (t, EXPECTED_FAILURES))
-            return new EMMARuntimeException (UNEXPECTED_FAILURE,
-                                            new Object [] {t.toString (), IAppConstants.APP_BUG_REPORT_LINK},
-                                            t);
-        else if (t instanceof RuntimeException)
-            return (RuntimeException) t;
-        else
-            return new EMMARuntimeException (t);
-    }
-    
-
-    // caller-settable state [scoped to this runner instance]:
-    
-    private final ClassLoader m_delegate;
-    
-    private String m_appClassName;      // required to be non-null for run()
-    private String [] m_appArgs;        // required to be non-null for run()
-    
-    private File [] m_coveragePath;     // required to be non-null/non-empty for run()
-    private boolean m_canonical;
-    private boolean m_scanCoveragePath;
-    private IInclExclFilter m_coverageFilter; // can be null for run()   
-    
-    private boolean m_dumpSessionData;
-    private File m_sdataOutFile; // user override; can be null for run()
-    private Boolean m_sdataOutMerge; // user override; can be null for run()
-   
-    private IReportGenerator [] m_reportGenerators; // required to be non-null for run()
-    private File [] m_sourcePath;                   // can be null/empty for run()
-    
-    // it is attractive to detect errors at load time, but this may allow
-    // threads created by <clinit> code to escape; on the other hand, classes
-    // that do not override main() will not get initialized this way and will
-    // not register with our runtime [which seems a minor problem at this point]: 
-    private static final boolean INIT_AT_LOAD_TIME = false;
-    
-    // setting the context loader on AppRunner's thread should not
-    // be necessary since the app is run in a dedicated thread group;
-    // however, if INIT_AT_LOAD_TIME=true the app's <clinit> code
-    // should run with an adjusted context loader:
-    private static final boolean SET_CURRENT_CONTEXT_LOADER = INIT_AT_LOAD_TIME;
-    
-    // a soft cache is ideal for managing class definitions that are read during
-    // the initial classpath scan; however, the default LRU policy parameters for
-    // clearing SoftReferences in Sun's J2SDK 1.3+ render them next to useless
-    // in the client HotSpot JVM (in which this tool will probably run most often);
-    // using a hard cache guarantees 100% cache hit rate but can also raise the
-    // memory requirements significantly beyond the needs of the original app.
-    // [see bug refs 4471453, 4806720, 4888056, 4239645]
-    //
-    // resolution for now: use a soft cache anyway and doc that to make it useful
-    // for non-trivial apps the user should use -Xms or -XX:SoftRefLRUPolicyMSPerMB
-    // JVM options or use a server HotSpot JVM
-    private static final boolean USE_SOFT_CACHE = true;
-    
-    private static final int INIT_CACHE_CAPACITY = 2003; // prime
-    private static final int SOFT_CACHE_READ_CHK_FREQUENCY = 100;
-    private static final int SOFT_CACHE_WRITE_CHK_FREQUENCY = 100;
-
-    private static final String [] FORCED_DELEGATION_FILTER_SPECS; // set in <clinit>
-    private static final Class [] MAIN_TYPE = new Class [] {String [].class};
-    
-    private static final Class [] EXPECTED_FAILURES; // set in <clinit>
-    
-    protected static final String COMMA_DELIMITERS    = "," + Strings.WHITE_SPACE;
-    protected static final String PATH_DELIMITERS     = ",".concat (File.pathSeparator);
-    
-    static
-    {
-        EXPECTED_FAILURES = new Class []
-        {
-            EMMARuntimeException.class,
-            IllegalArgumentException.class,
-            IllegalStateException.class,
-        };
-                
-        FORCED_DELEGATION_FILTER_SPECS = new String [] {"+" + IAppConstants.APP_PACKAGE + ".*"};
-    }
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/rt/ClassPathCacheEntry.java b/core/java12/com/vladium/emma/rt/ClassPathCacheEntry.java
deleted file mode 100644
index a8361b4..0000000
--- a/core/java12/com/vladium/emma/rt/ClassPathCacheEntry.java
+++ /dev/null
@@ -1,47 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ClassPathCacheEntry.java,v 1.1.1.1 2004/05/09 16:57:43 vlad_r Exp $
- */
-package com.vladium.emma.rt;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class ClassPathCacheEntry
-{
-    // public: ................................................................
-    
-    // getters not provided [the fields are final]
-    
-    public final byte [] m_bytes;
-    public final String m_srcURL; // a String is more compact that java.net.URL
-    
-    
-    public ClassPathCacheEntry (final byte [] bytes, final String srcURL)
-    {
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (bytes != null, "bytes = null");
-            $assert.ASSERT (srcURL != null, "srcURL = null");
-        }
-        
-        m_bytes = bytes;
-        m_srcURL = srcURL;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/rt/ClassPathProcessorST.java b/core/java12/com/vladium/emma/rt/ClassPathProcessorST.java
deleted file mode 100644
index 2e06948..0000000
--- a/core/java12/com/vladium/emma/rt/ClassPathProcessorST.java
+++ /dev/null
@@ -1,397 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ClassPathProcessorST.java,v 1.1.1.1.2.1 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma.rt;
-
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileNotFoundException;
-import java.io.IOException;
-import java.io.InputStream;
-import java.util.Map;
-import java.util.jar.JarInputStream;
-import java.util.jar.Manifest;
-import java.util.zip.ZipEntry;
-import java.util.zip.ZipInputStream;
-
-import com.vladium.jcd.cls.ClassDef;
-import com.vladium.jcd.parser.ClassDefParser;
-import com.vladium.logging.Logger;
-import com.vladium.util.ByteArrayOStream;
-import com.vladium.util.Files;
-import com.vladium.util.IPathEnumerator;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.IAppErrorCodes;
-import com.vladium.emma.EMMARuntimeException;
-import com.vladium.emma.data.IMetaData;
-import com.vladium.emma.filter.IInclExclFilter;
-import com.vladium.emma.instr.InstrVisitor;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class ClassPathProcessorST implements IPathEnumerator.IPathHandler, IAppErrorCodes
-{
-    // public: ................................................................
-    
-    public void run ()
-    {
-        long start = System.currentTimeMillis ();
-        
-        // construct instr path enumerator [throws on illegal input only]:
-        final IPathEnumerator enumerator = IPathEnumerator.Factory.create (m_path, m_canonical, this);
-        
-        // allocate I/O buffers:
-        m_readbuf = new byte [BUF_SIZE]; // don't reuse this across run() calls to reset it to the original size
-        m_readpos = 0;
-        m_baos = new ByteArrayOStream (BUF_SIZE); // don't reuse this across run() calls to reset it to the original size
-        
-        if (m_log.atINFO ())
-        {
-            m_log.info ("processing classpath ...");
-        }
-        
-        // actual work is driven by the path enumerator:
-        try
-        {
-            enumerator.enumerate ();
-        }
-        catch (IOException ioe)
-        {
-            throw new EMMARuntimeException (INSTR_IO_FAILURE, ioe);
-        }
-        
-        if (m_log.atINFO ())
-        {
-            final long end = System.currentTimeMillis ();
-            
-            m_log.info ("[" + m_classCount + " class(es) processed in " + (end - start) + " ms]");
-        }
-    }
-    
-    // IPathEnumerator.IPathHandler:
-
-    public void handleArchiveStart (final File parentDir, final File archive, final Manifest manifest)
-    {
-        m_archiveFile = Files.newFile (parentDir, archive.getPath ());
-    }
-
-    public void handleArchiveEntry (final JarInputStream in, final ZipEntry entry)
-    {
-        if (m_log.atTRACE2 ()) m_log.trace2 ("handleArchiveEntry", "[" + entry.getName () + "]");
-        
-        final String name = entry.getName ();
-        final String lcName = name.toLowerCase ();
-        
-        if (lcName.endsWith (".class"))
-        {
-            final String className = name.substring (0, name.length () - 6).replace ('/', '.');
-            
-            if ((m_coverageFilter == null) || m_coverageFilter.included (className))
-            {
-                String srcURL = null;
-                InputStream clsin = null;
-                try
-                {
-                    readZipEntry (in, entry);
-                    
-                    srcURL = "jar:".concat (m_archiveFile.toURL ().toExternalForm ()).concat ("!/").concat (name);
-                }
-                catch (FileNotFoundException fnfe)
-                {
-                    // ignore: this should never happen
-                    if ($assert.ENABLED)
-                    {
-                        fnfe.printStackTrace (System.out);
-                    }
-                }
-                catch (IOException ioe)
-                {
-                    // TODO: error code
-                    throw new EMMARuntimeException (ioe);
-                }
-                finally
-                {
-                    if (clsin != null)
-                        try
-                        {
-                            clsin.close ();
-                            clsin = null;
-                        }
-                        catch (Exception e)
-                        {
-                            // TODO: error code
-                            throw new EMMARuntimeException (e);
-                        }
-                }
-                
-                // [original class def read into m_readbuf]
-                
-                try
-                {
-                    ClassDef clsDef = ClassDefParser.parseClass (m_readbuf, m_readpos);
-                    if (! clsDef.isInterface ()) ++ m_classCount;
-                    
-                    m_visitor.process (clsDef, false, false, true, m_instrResult); // get metadata only
-                    clsDef = null;
-                    
-                    boolean cacheClassDef = true;
-                  
-                    if (m_instrResult.m_descriptor != null)
-                    {
-                        // do not overwrite existing descriptors to support "first
-                        // in the classpath wins" semantics:
-                        
-                        if (! m_mdata.add (m_instrResult.m_descriptor, false))
-                           cacheClassDef = false; 
-                    }
-                    
-                    if (cacheClassDef && (m_cache != null))
-                    {
-                        final byte [] bytes = new byte [m_readpos];
-                        System.arraycopy (m_readbuf, 0, bytes, 0, m_readpos);
-                        
-                        m_cache.put (className, new ClassPathCacheEntry (bytes, srcURL));
-                    }
-                }
-                catch (IOException ioe)
-                {
-                    // TODO: error code
-                    throw new EMMARuntimeException (ioe);
-                }
-            }
-        }
-    }
-
-    public void handleArchiveEnd (final File parentDir, final File archive)
-    {
-        m_archiveFile = null;
-    }
-
-
-    public void handleDirStart (final File pathDir, final File dir)
-    {
-        // do nothing
-    }
-
-    public void handleFile (final File pathDir, final File file)
-    {
-        if (m_log.atTRACE2 ()) m_log.trace2 ("handleFile", "[" + pathDir + "] [" + file + "]");
-        
-        final String name = file.getPath ();
-        final String lcName = name.toLowerCase ();
-        
-        if (lcName.endsWith (".class"))
-        {
-            final String className = name.substring (0, name.length () - 6).replace (File.separatorChar, '.');
-            
-            if ((m_coverageFilter == null) || m_coverageFilter.included (className))
-            {
-                String srcURL = null;
-                InputStream clsin = null;
-                try
-                {
-                    final File inFile = Files.newFile (pathDir, file.getPath ());
-                    readFile (inFile);
-                    
-                    srcURL = inFile.toURL ().toExternalForm ();
-                }
-                catch (FileNotFoundException fnfe)
-                {
-                    // ignore: this should never happen
-                    if ($assert.ENABLED)
-                    {
-                        fnfe.printStackTrace (System.out);
-                    }
-                }
-                catch (IOException ioe)
-                {
-                    // TODO: error code
-                    throw new EMMARuntimeException (ioe);
-                }
-                finally
-                {
-                    if (clsin != null)
-                        try
-                        {
-                            clsin.close ();
-                            clsin = null;
-                        }
-                        catch (Exception e)
-                        {
-                            // TODO: error code
-                            throw new EMMARuntimeException (e);
-                        }
-                }
-                
-                // [original class def read into m_readbuf]
-                
-                try
-                {
-                    ClassDef clsDef = ClassDefParser.parseClass (m_readbuf, m_readpos);
-                    if (! clsDef.isInterface ()) ++ m_classCount;
-                    
-                    m_visitor.process (clsDef, false, false, true, m_instrResult); // get metadata only
-                    clsDef = null;
-                    
-                    
-                    boolean cacheClassDef = true;
-                  
-                    if (m_instrResult.m_descriptor != null)
-                    {
-                        // do not overwrite existing descriptors to support "first
-                        // in the classpath wins" semantics:
-                        
-                        if (! m_mdata.add (m_instrResult.m_descriptor, false))
-                           cacheClassDef = false; 
-                    }
-                    
-                    if (cacheClassDef && (m_cache != null))
-                    {
-                        final byte [] bytes = new byte [m_readpos];
-                        System.arraycopy (m_readbuf, 0, bytes, 0, m_readpos);
-                        
-                        m_cache.put (className, new ClassPathCacheEntry (bytes, srcURL));
-                    }
-                }
-                catch (IOException ioe)
-                {
-                    // TODO: error code
-                    throw new EMMARuntimeException (ioe);
-                }
-            }
-        }
-    }
-
-    public void handleDirEnd (final File pathDir, final File dir)
-    {
-        // do nothing
-    }
-
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    /*
-     * null 'cache' indicates to only populate the metadata and not bother with
-     * caching instrumented class defs
-     */
-    ClassPathProcessorST (final File [] path, final boolean canonical,
-                          final IMetaData mdata, final IInclExclFilter filter,
-                          final Map cache)
-    {
-        if (path == null) throw new IllegalArgumentException ("null input: path");
-        if (mdata == null) throw new IllegalArgumentException ("null input: mdata");
-        
-        m_path = path;
-        m_canonical = canonical;
-        m_mdata = mdata;
-        m_coverageFilter = filter;
-        m_cache = cache; // can be null
-        m_visitor = new InstrVisitor (mdata.getOptions ());
-        m_instrResult = new InstrVisitor.InstrResult ();
-        
-        m_log = Logger.getLogger ();
-    }
-
-    // private: ...............................................................
-
-
-    /*
-     * Reads into m_readbuf (m_readpos is updated correspondingly)
-     */
-    private void readFile (final File file)
-        throws IOException
-    {
-        final int length = (int) file.length ();
-        
-        ensureReadCapacity (length);
-        
-        InputStream in = null;
-        try
-        {
-            in = new FileInputStream (file);
-            
-            int totalread = 0;
-            for (int read;
-                 (totalread < length) && (read = in.read (m_readbuf, totalread, length - totalread)) >= 0;
-                 totalread += read);
-            m_readpos = totalread;
-        } 
-        finally
-        {
-            if (in != null) try { in.close (); } catch (Exception ignore) {} 
-        }
-    }
-    
-    /*
-     * Reads into m_readbuf (m_readpos is updated correspondingly)
-     */
-    private void readZipEntry (final ZipInputStream in, final ZipEntry entry)
-        throws IOException
-    {
-        final int length = (int) entry.getSize (); // can be -1 if unknown
-        
-        if (length >= 0)
-        {
-            ensureReadCapacity (length);
-            
-            int totalread = 0;
-            for (int read;
-                 (totalread < length) && (read = in.read (m_readbuf, totalread, length - totalread)) >= 0;
-                 totalread += read);
-            m_readpos = totalread;
-        }
-        else
-        {
-            ensureReadCapacity (BUF_SIZE);
-            
-            m_baos.reset ();
-            for (int read; (read = in.read (m_readbuf)) >= 0; m_baos.write (m_readbuf, 0, read));
-            
-            m_readbuf = m_baos.copyByteArray ();
-            m_readpos = m_readbuf.length;
-        }
-    }   
- 
-    private void ensureReadCapacity (final int capacity)
-    {
-        if (m_readbuf.length < capacity)
-        {
-            final int readbuflen = m_readbuf.length;
-            m_readbuf = null;
-            m_readbuf = new byte [Math.max (readbuflen << 1, capacity)];
-        }
-    }
-
-
-    private final File [] m_path; // never null
-    private final boolean m_canonical;
-    private final IMetaData m_mdata; // never null
-    private final IInclExclFilter m_coverageFilter; // can be null
-    private final InstrVisitor m_visitor;
-    private final InstrVisitor.InstrResult m_instrResult;
-    private final Map /* classJavaName:String -> ClassPathCacheEntry */ m_cache; // can be null
-    
-    private final Logger m_log; // this class is instantiated and used on a single thread
-    
-    private int m_classCount;
-    
-    private byte [] m_readbuf;
-    private int m_readpos;
-    private ByteArrayOStream m_baos; // TODO: code to guard this from becoming too large
-    
-    private File m_archiveFile;
-    
-    private static final int BUF_SIZE = 32 * 1024;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/rt/IClassLoadHook.java b/core/java12/com/vladium/emma/rt/IClassLoadHook.java
deleted file mode 100644
index 57c01e5..0000000
--- a/core/java12/com/vladium/emma/rt/IClassLoadHook.java
+++ /dev/null
@@ -1,73 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IClassLoadHook.java,v 1.1.1.1 2004/05/09 16:57:44 vlad_r Exp $
- */
-package com.vladium.emma.rt;
-
-import java.io.IOException;
-
-import com.vladium.util.ByteArrayOStream;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, 2003
- */
-public
-interface IClassLoadHook
-{
-    // public: ................................................................
-
-//    /**
-//     * The hook returns 'true' or 'false' based on 'className' only. If it
-//     * returns false, the current loader will load the class bytes itself and
-//     * pass them to ClassLoader.defineClass() unchanged. This is an optimization
-//     * to let the JVM native code do the parsing of class definitions for classes
-//     * that do not match coverage filters instead of doing this in bytecode.  
-//     */
-//    boolean interested (String className);
-    
-    // TODO: figure out a way to avoid all this excessive copying of byte arrays
-    
-    /* TODO: finish
-     * 
-     * The hook reads in the original class definition from 'in' and [possibly]
-     * instruments it, returning the modified class definion [which should
-     * correspond to the original class name]. Only class definitions with names
-     * that were successfully filtered via a previous (although not necessarily
-     * <em>immediately</em> so) call to {@link #interested} will be passed to
-     * this method.<P>
-     * 
-     * It is possible that the hook will determine that it is not interested in
-     * intrumenting the pending class definition [or is unable to do so] only
-     * after reading some content from 'in'. An example would be when the class
-     * definition turns out to be for an interface and the hook does not process
-     * interfaces. Because 'in' can then be left in an uncertain state, the hook
-     * must follow these rules for the two possible outcomes:
-     * <ol>
-     *  <li> if the hook can successfully recover the unmodified class definion
-     * [perhaps because it cloned the original definition or never modified it]:
-     * it should write it into 'out' and return 'true';
-     *  <li> if the hook has lost the original class definion: it should return 'false'.
-     * Following that, the current loader will close() and discard 'in' and load
-     * the class from another, equivalent in content, data stream instance. 
-     * </ol>
-     * 
-     * In any case 'in' and 'out' remain owned [and will be close()d] by the caller.
-     * 
-     * NOTE: the hook should only write to 'out' after reading the entire
-     * class definition in 'bytes' ('out' could be backed by the same array as
-     * 'bytes')
-     * 
-     * @param out [buffered by the caller]
-     */
-    boolean processClassDef (String className,
-                             byte [] bytes, int length,
-                             ByteArrayOStream out)
-        throws IOException;
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/rt/InstrClassLoadHook.java b/core/java12/com/vladium/emma/rt/InstrClassLoadHook.java
deleted file mode 100644
index ff51cc4..0000000
--- a/core/java12/com/vladium/emma/rt/InstrClassLoadHook.java
+++ /dev/null
@@ -1,136 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: InstrClassLoadHook.java,v 1.1.1.1 2004/05/09 16:57:44 vlad_r Exp $
- */
-package com.vladium.emma.rt;
-
-import java.io.IOException;
-
-import com.vladium.jcd.cls.ClassDef;
-import com.vladium.jcd.compiler.ClassWriter;
-import com.vladium.jcd.parser.ClassDefParser;
-import com.vladium.util.ByteArrayOStream;
-import com.vladium.util.Descriptors;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.filter.IInclExclFilter;
-import com.vladium.emma.instr.InstrVisitor;
-import com.vladium.emma.data.CoverageOptions;
-import com.vladium.emma.data.IMetaData;
-
-// ----------------------------------------------------------------------------
-/**
- * MT-safety ensured by the containing loader
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class InstrClassLoadHook implements IClassLoadHook
-{
-    // public: ................................................................
-    
-    /**
-     * @param filter [can be null]
-     */
-    public InstrClassLoadHook (final IInclExclFilter filter, final IMetaData mdata)
-    {
-        if (mdata == null) throw new IllegalArgumentException ("null input: mdata");
-        
-        m_filter = filter; // can be null 
-        m_metadata = mdata;
-        
-        // important to use the same options as the metadata may have been populated earlier:
-        final CoverageOptions options = mdata.getOptions ();
-        m_classDefProcessor = new InstrVisitor (options);
-        
-        m_instrResult = new InstrVisitor.InstrResult ();
-    }
-    
-        
-    public boolean processClassDef (final String className,
-                                    final byte [] bytes, final int length,
-                                    ByteArrayOStream out)
-        throws IOException
-    {
-        if ($assert.ENABLED)
-        {
-            $assert.ASSERT (className != null, "className is null");
-            $assert.ASSERT (bytes != null, "bytes is null");
-            $assert.ASSERT (bytes != null, "out is null");
-        }
-        
-        final IInclExclFilter filter = m_filter;
-        if ((filter == null) || filter.included (className))
-        {
-            final ClassDef clsDef = ClassDefParser.parseClass (bytes, length);
-            final String classVMName = Descriptors.javaNameToVMName (className);
-            
-            final Object lock = m_metadata.lock ();
-            
-            final boolean metadataExists;
-            synchronized (lock)
-            {
-                metadataExists = m_metadata.hasDescriptor (classVMName);
-            }
-            
-            // since this is the first [and only] time the parent loader is
-            // loading the class in question, if metadata for 'className' exists
-            // it means it was created during the app runner's classpath scan --
-            // do not overwrite it (the class def should be the same)
-            
-            // [this picture breaks down if the design changes so that the same
-            // metadata instance could be associated with more than one app loader]
-            
-            m_classDefProcessor.process (clsDef, false, true, ! metadataExists, m_instrResult);
-            
-            boolean useOurs = m_instrResult.m_instrumented;
-            
-            if (m_instrResult.m_descriptor != null) // null means either the metadata existed already or the class is an interface
-            {
-                // try to update metadata [this supports the "no initial full cp
-                // scan mode" in the app runner and also ensures that we pick up
-                // any dynamically generated classes to support (hacky) apps that
-                // do dynamic source generation/compilation]:
-                
-                synchronized (lock)
-                {
-                    // do not force overwrites of existing descriptors to support
-                    // correct handling of race conditions: if another thread
-                    // updates the metadata first, discard our version of the class def
-                    
-                    // [actually, this guard is redundant here because
-                    // right now the hook can only have a single classloader parent
-                    // and the parent's loadClass() is a critical section]
-                    
-                    if (! m_metadata.add (m_instrResult.m_descriptor, false))
-                         useOurs = false; 
-                }
-            }
-            
-            if (useOurs)
-            {                        
-                ClassWriter.writeClassTable (clsDef, out);
-                return true;
-            }
-        }
-
-        return false;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private final IInclExclFilter m_filter; // can be null [equivalent to no filtering]
-    private final IMetaData m_metadata; // never null
-    private final InstrVisitor m_classDefProcessor; // never null
-    private final InstrVisitor.InstrResult m_instrResult;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/rt/InstrClassLoader.java b/core/java12/com/vladium/emma/rt/InstrClassLoader.java
deleted file mode 100644
index 7732d0e..0000000
--- a/core/java12/com/vladium/emma/rt/InstrClassLoader.java
+++ /dev/null
@@ -1,463 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: InstrClassLoader.java,v 1.1.1.1.2.2 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma.rt;
-
-import java.io.File;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.PrintWriter;
-import java.net.MalformedURLException;
-import java.net.URL;
-import java.net.URLClassLoader;
-import java.security.CodeSource;
-import java.security.cert.Certificate;
-import java.util.Map;
-
-import com.vladium.logging.Logger;
-import com.vladium.util.ByteArrayOStream;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.filter.IInclExclFilter;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class InstrClassLoader extends URLClassLoader
-{
-    // public: ................................................................
-        
-    // TODO: proper security [use PrivilegedAction as needed]
-    // TODO: [see above as well] need to keep track of res URLs to support [path] exclusion patterns
-    // TODO: improve error handling so it is clear when errors come from buggy instrumentation
-    
-    
-    public static final String PROPERTY_FORCED_DELEGATION_FILTER  = "clsload.forced_delegation_filter";
-    public static final String PROPERTY_THROUGH_DELEGATION_FILTER  = "clsload.through_delegation_filter";
-        
-
-    public InstrClassLoader (final ClassLoader parent, final File [] classpath,
-                             final IInclExclFilter forcedDelegationFilter,
-                             final IInclExclFilter throughDelegationFilter,
-                             final IClassLoadHook hook, final Map cache)
-        throws MalformedURLException
-    {
-        // setting ClassLoader.parent to null disables the standard delegation
-        // behavior in a few places, including URLClassLoader.getResource():
-        
-        super (filesToURLs (classpath), null);
-        
-        // TODO: arg validation
-        
-        m_hook = hook;
-        m_cache = cache; // can be null
-        
-        m_forcedDelegationFilter = forcedDelegationFilter;
-        m_throughDelegationFilter = throughDelegationFilter;
-         
-        m_parent = parent;        
-        m_bufPool = new PoolEntry [BAOS_POOL_SIZE];
-        
-        m_log = Logger.getLogger ();
-    }
-    
-    /**
-     * Overrides java.lang.ClassLoader.loadClass() to change the usual parent-child
-     * delegation rules just enough to be able to 'replace' the parent loader. This
-     * also has the effect of detecting 'system' classes without doing any class
-     * name-based matching.
-     */
-    public synchronized final Class loadClass (final String name, final boolean resolve)
-        throws ClassNotFoundException
-    {
-        final boolean trace1 = m_log.atTRACE1 ();
-        
-        if (trace1) m_log.trace1 ("loadClass",  "(" + name + ", " + resolve + "): nest level " + m_nestLevel);
-        
-        Class c = null;
-        
-        // first, check if this class has already been defined by this classloader
-        // instance:
-        c = findLoadedClass (name);
-        
-        if (c == null)
-        {
-            Class parentsVersion = null;
-            if (m_parent != null)
-            {
-                try
-                {
-                    parentsVersion = m_parent.loadClass (name); // note: it is important that this does not init the class
-                    
-                    if ((parentsVersion.getClassLoader () != m_parent) ||
-                        ((m_forcedDelegationFilter == null) || m_forcedDelegationFilter.included (name)))
-                    {
-                        // (a) m_parent itself decided to delegate: use parent's version
-                        // (b) the class was on the forced delegation list: use parent's version
-                        c = parentsVersion;
-                        if (trace1) m_log.trace1 ("loadClass", "using parent's version for [" + name + "]");
-                    }
-                }
-                catch (ClassNotFoundException cnfe)
-                {
-                    // if the class was on the forced delegation list, error out: 
-                    if ((m_forcedDelegationFilter == null) || m_forcedDelegationFilter.included (name))
-                        throw cnfe;
-                }
-            }
-            
-            if (c == null)
-            {
-                try
-                {
-                    // either (a) m_parent was null or (b) it could not load 'c'
-                    // or (c) it will define 'c' itself if allowed to. In any
-                    // of these cases I attempt to define my own version:
-                    c = findClass (name);
-                }
-                catch (ClassNotFoundException cnfe)
-                {
-                    // this is a difficult design point unless I resurrect the -lx option
-                    // and document how to use it [which will confuse most users anyway]
-                    
-                    // another alternative would be to see if parent's version is included by
-                    // the filter and print a warning; still, it does not help with JAXP etc 
-                    
-                    if (parentsVersion != null)
-                    {
-                        final boolean delegate = (m_throughDelegationFilter == null) || m_throughDelegationFilter.included (name); 
-                        
-                        if (delegate)
-                        {
-                            c = parentsVersion;
-                            if (trace1) m_log.trace1 ("loadClass", "[delegation filter] using parent's version for [" + name + "]");
-                        }
-                        else
-                            throw cnfe;
-                    }
-                    else
-                      throw cnfe;
-                }
-            }
-        }
-        
-        if (c == null) throw new ClassNotFoundException (name);
-        
-        if (resolve) resolveClass (c); // this never happens in J2SE JVMs
-        return c;
-    }
-    
-    // TODO: remove this in the release build
-    
-    public final URL getResource (final String name)
-    {
-        final boolean trace1 = m_log.atTRACE1 ();
-        
-        if (trace1) m_log.trace1 ("getResource",  "(" + name + "): nest level " + m_nestLevel);
-        
-        final URL result = super.getResource (name);
-        if (trace1 && (result != null)) m_log.trace1 ("loadClass",  "[" + name + "] found in " + result);
-        
-        return result;
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected final Class findClass (final String name)
-        throws ClassNotFoundException
-    {
-        final boolean trace1 = m_log.atTRACE1 ();
-        
-        if (trace1) m_log.trace1 ("findClass",  "(" + name + "): nest level " + m_nestLevel);
-        
-        final boolean useClassCache = (m_cache != null);
-        final ClassPathCacheEntry entry = useClassCache ? (ClassPathCacheEntry) m_cache.remove (name) : null;
-        
-        byte [] bytes;
-        int length;
-        URL classURL = null;
-            
-        if (entry != null) // cache hit
-        {
-            ++ m_cacheHits;
-            
-            // used cached class def bytes, no need to repeat disk I/O:
-            
-            try
-            {
-                classURL = new URL (entry.m_srcURL);
-            }
-            catch (MalformedURLException murle) // this should never happen
-            {
-                if ($assert.ENABLED)
-                {
-                    murle.printStackTrace (System.out);
-                }
-            }
-            
-            PoolEntry buf = null;
-            try
-            {
-                buf = acquirePoolEntry ();
-                final ByteArrayOStream baos = buf.m_baos; // reset() has been called on this
-                
-                // the original class definition:
-                bytes = entry.m_bytes;
-                length = bytes.length;
-                
-                if ((m_hook != null) && m_hook.processClassDef (name, bytes, length, baos)) // note: this can overwrite 'bytes'
-                {
-                    // the instrumented class definition:
-                    bytes = baos.getByteArray ();
-                    length = baos.size ();
-                    
-                    if (trace1) m_log.trace1 ("findClass",  "defining [cached] instrumented [" + name + "] {" + length + " bytes }");
-                }
-                else
-                {
-                    if (trace1) m_log.trace1 ("findClass",  "defining [cached] [" + name + "] {" + length + " bytes }");
-                }
-                
-                return defineClass (name, bytes, length, classURL);
-            }
-            catch (IOException ioe)
-            {
-                throw new ClassNotFoundException (name);
-            }
-            finally
-            {
-                if (buf != null) releasePoolEntry (buf);
-            }
-        }
-        else // cache miss
-        {
-            if (useClassCache) ++ m_cacheMisses;
-            
-            // .class files are not guaranteed to be loadable as resources;
-            // but if Sun's code does it...
-            final String classResource = name.replace ('.', '/') + ".class";
-            
-            // even thought normal delegation is disabled, this will find bootstrap classes:
-            classURL = getResource (classResource); // important to hook into URLClassLoader's overload of this so that Class-Path manifest attributes are processed etc
-            
-            if (trace1 && (classURL != null)) m_log.trace1 ("findClass",  "[" + name + "] found in " + classURL);
-            
-            if (classURL == null)
-                throw new ClassNotFoundException (name);
-            else
-            {
-                InputStream in = null;
-                PoolEntry buf = null;
-                try
-                {
-                    in = classURL.openStream ();
-                    
-                    buf = acquirePoolEntry ();
-                    final ByteArrayOStream baos = buf.m_baos; // reset() has been called on this
-                    
-                    readFully (in, baos, buf.m_buf);
-                    in.close (); // don't keep the file handle across reentrant calls
-                    in = null;
-                    
-                    // the original class definition:
-                    bytes = baos.getByteArray ();
-                    length = baos.size ();
-                    
-                    baos.reset (); // reuse this for processClassDef below
-                    
-                    if ((m_hook != null) && m_hook.processClassDef (name, bytes, length, baos)) // note: this can overwrite 'bytes'
-                    {
-                        // the instrumented class definition:
-                        bytes = baos.getByteArray ();
-                        length = baos.size ();
-                        
-                        if (trace1) m_log.trace1 ("findClass",  "defining instrumented [" + name + "] {" + length + " bytes }");
-                    }
-                    else
-                    {
-                        if (trace1) m_log.trace1 ("findClass",  "defining [" + name + "] {" + length + " bytes }");
-                    }
-                    
-                    return defineClass (name, bytes, length, classURL);
-                }
-                catch (IOException ioe)
-                {
-                    throw new ClassNotFoundException (name);
-                }
-                finally
-                {
-                    if (buf != null) releasePoolEntry (buf);
-                    if (in != null) try { in.close (); } catch (Exception ignore) {}
-                }
-            }
-        }
-    }
-    
-    public void debugDump (final PrintWriter out)
-    {
-        if (out != null)
-        {
-            out.println (this + ": " + m_cacheHits + " class cache hits, " + m_cacheMisses + " misses");
-        }
-    }
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final class PoolEntry
-    {
-        PoolEntry (final int baosCapacity, final int bufSize)
-        {
-            m_baos = new ByteArrayOStream (baosCapacity);
-            m_buf = new byte [bufSize];
-        }
-        
-        void trim (final int baosCapacity, final int baosMaxCapacity)
-        {
-            if (m_baos.capacity () > baosMaxCapacity)
-            {
-                m_baos = new ByteArrayOStream (baosCapacity);
-            }
-        }
-        
-        ByteArrayOStream m_baos;
-        final byte [] m_buf;
-        
-    } // end of nested class
-    
-    
-    /*
-     * 'srcURL' may be null
-     */
-    private Class defineClass (final String className, final byte [] bytes, final int length, final URL srcURL)
-    {
-        // support ProtectionDomains with non-null class source URLs:
-        // [however, disable anything related to sealing or signing]
-        
-        final CodeSource csrc = new CodeSource (srcURL, (Certificate[])null);
-        
-        // allow getPackage() to return non-null on the class we are about to
-        // define (however, don't bother emulating the original manifest info since
-        // we may be altering manifest content anyway):
-        
-        final int lastDot = className.lastIndexOf ('.');
-        if (lastDot >= 0)
-        {
-            final String packageName = className.substring (0, lastDot);
-            
-            final Package pkg = getPackage (packageName);
-            if (pkg == null)
-            {
-                definePackage (packageName,
-                               IAppConstants.APP_NAME, IAppConstants.APP_VERSION, IAppConstants.APP_COPYRIGHT,
-                               IAppConstants.APP_NAME, IAppConstants.APP_VERSION, IAppConstants.APP_COPYRIGHT,
-                               srcURL);
-            }
-        }
-        
-        return defineClass (className, bytes, 0, length, csrc);
-    }
-    
-    
-    private static URL [] filesToURLs (final File [] classpath)
-        throws MalformedURLException
-    {
-        if ((classpath == null) || (classpath.length == 0))
-            return EMPTY_URL_ARRAY;
-            
-        final URL [] result = new URL [classpath.length];
-        
-        for (int f = 0; f < result.length ; ++ f)
-        {
-            result [f] = classpath [f].toURL (); // note: this does proper dir encoding
-        }
-        
-        return result;
-    }
-    
-    /**
-     * Reads the entire contents of a given stream into a flat byte array.
-     */
-    private static void readFully (final InputStream in, final ByteArrayOStream out, final byte [] buf)
-        throws IOException
-    {
-        for (int read; (read = in.read (buf)) >= 0; )
-        {
-            out.write (buf, 0, read);
-        }
-    }
-    
-    /*
-     * not MT-safe; must be called from loadClass() only
-     */
-    private PoolEntry acquirePoolEntry ()
-    {
-        PoolEntry result;
-        
-        if (m_nestLevel >= BAOS_POOL_SIZE)
-        {
-            result = new PoolEntry (BAOS_INIT_SIZE, BAOS_INIT_SIZE);
-        }
-        else
-        {
-            result = m_bufPool [m_nestLevel];
-            if (result == null)
-            {
-                result = new PoolEntry (BAOS_INIT_SIZE, BAOS_INIT_SIZE);
-                m_bufPool [m_nestLevel] = result;
-            }
-            else
-            {
-                result.m_baos.reset ();
-            }
-        }
-        
-        ++ m_nestLevel;
-            
-        return result;
-    }
-    
-    /*
-     * not MT-safe; must be called from loadClass() only
-     */
-    private void releasePoolEntry (final PoolEntry buf)
-    {
-        if (-- m_nestLevel < BAOS_POOL_SIZE)
-        {
-            buf.trim (BAOS_INIT_SIZE, BAOS_MAX_SIZE);
-        }
-    }
-    
-    
-    private final ClassLoader m_parent;    
-    
-    private final IInclExclFilter m_forcedDelegationFilter;
-    private final IInclExclFilter m_throughDelegationFilter;
-    
-    private final Map /* classJavaName:String -> ClassPathCacheEntry */ m_cache; // can be null
-    private final IClassLoadHook m_hook;
-    private final PoolEntry [] m_bufPool;
-    
-    private final Logger m_log; // a loader instance is used concurrently but cached its log config at construction time
-    
-    private int m_nestLevel;
-    
-    private int m_cacheHits, m_cacheMisses;
-    
-    private static final int BAOS_INIT_SIZE = 32 * 1024;
-    private static final int BAOS_MAX_SIZE = 1024 * 1024;
-    private static final int BAOS_POOL_SIZE = 8;
-    private static final URL [] EMPTY_URL_ARRAY = new URL [0];
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/emma/rt/RT.java b/core/java12/com/vladium/emma/rt/RT.java
deleted file mode 100644
index 9273348..0000000
--- a/core/java12/com/vladium/emma/rt/RT.java
+++ /dev/null
@@ -1,255 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: RT.java,v 1.2.2.3 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma.rt;
-
-import java.io.File;
-
-import com.vladium.logging.Logger;
-import com.vladium.util.IProperties;
-import com.vladium.util.Property;
-import com.vladium.util.exit.ExitHookManager;
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.EMMAProperties;
-import com.vladium.emma.data.ICoverageData;
-import com.vladium.emma.data.DataFactory;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class RT implements IAppConstants
-{
-    // public: ................................................................
-    
-    
-    public static synchronized ICoverageData reset (final boolean createCoverageData, final boolean createExitHook)
-    {
-        // reload the app properties [needs to be done to accomodate classloader rearrangements]:
-        
-        // avoid the call context tricks at runtime in case security causes problems,
-        // use an explicit caller parameter for getAppProperties():
-        
-        ClassLoader loader = RT.class.getClassLoader ();
-        if (loader == null) loader = ClassLoader.getSystemClassLoader (); 
-        
-        IProperties appProperties = null;
-        try
-        {
-            appProperties = EMMAProperties.getAppProperties (loader);
-        }
-        catch (Throwable t)
-        {
-            // TODO: handle better
-            t.printStackTrace (System.out);
-        }
-        s_appProperties = appProperties;
-
-
-        if (EXIT_HOOK_MANAGER != null)
-        {
-            // disable/remove the current hook, if any:
-            
-            if (s_exitHook != null)
-            {
-                 // note: no attempt is made to execute the existing hook, so its coverage
-                 // data may be simply discarded
-                
-                EXIT_HOOK_MANAGER.removeExitHook (s_exitHook);
-                s_exitHook = null;
-            }
-        }
-        
-        ICoverageData cdata = s_cdata; // no sync accessor needed
-        if (createCoverageData)
-        {
-            cdata = DataFactory.newCoverageData ();
-            s_cdata = cdata;
-        }
-        else
-        {
-            s_cdata = null;
-        }
-        
-        if (EXIT_HOOK_MANAGER != null)
-        {
-            if (createExitHook && (cdata != null))
-            {
-                final Runnable exitHook = new RTExitHook (RT.class, cdata, getCoverageOutFile (), getCoverageOutMerge ());
-
-                // FR SF978671: fault all classes that we might need to do coverage
-                // data dumping (this forces classdefs to be loaded into classloader
-                // class cache and allows output file writing to succeed even if
-                // the RT classloader is some component loader (e.g, in a J2EE container)
-                // that gets invalidated by the time the exit hook thread is run:
-                
-                RTExitHook.createClassLoaderClosure ();
-                
-                if (EXIT_HOOK_MANAGER.addExitHook (exitHook))
-                {
-                    s_exitHook = exitHook;
-                }
-                // else TODO: log/warn
-            }
-        }
-        
-        return cdata;
-    }
-    
-    public static void r (final boolean [][] coverage, final String classVMName, final long stamp)
-    {
-        // note that we use class names, not the actual Class objects, as the keys here. This
-        // is not the best possible solution because it is not capable of supporting
-        // multiply (re)loaded classes within the same app, but the rest of the toolkit
-        // isn't designed to support this anyway. Furthermore, this does not interfere
-        // with class unloading.
-
-        final ICoverageData cdata = getCoverageData (); // need to use accessor for JMM reasons
-
-        // ['cdata' can be null if a previous call to dumpCoverageData() disabled data collection]
-        
-        if (cdata != null)
-        {
-            synchronized (cdata.lock ())
-            {
-                // TODO: could something useful be communicated back to the class
-                // by returning something here [e.g., unique class ID (solves the
-                // issues of class name collisions and class reloading) or RT.class
-                // (to prevent RT reloading)]
-                
-                cdata.addClass (coverage, classVMName, stamp);
-            }
-        }
-    }
-
-    public static synchronized ICoverageData getCoverageData ()
-    {
-        return s_cdata;
-    }
-    
-    public static synchronized IProperties getAppProperties ()
-    {
-        return s_appProperties;
-    }
-    
-    /**
-     * Public API for forcing coverage data dump.
-     * 
-     * @param outFile
-     * @param merge
-     * @param stopDataCollection
-     */
-    public static synchronized void dumpCoverageData (File outFile, final boolean merge, final boolean stopDataCollection)
-    {
-        if (DEBUG) System.out.println ("RT::dumpCoverageData() DUMPING " + RT.class.getClassLoader ());
-        outFile = outFile != null ? outFile : getCoverageOutFile ();
-        
-        ICoverageData cdata = s_cdata; // no need to use accessor
-        if (stopDataCollection) s_cdata = null; // TODO: log this NOTE: this does not really stop data collection, merely prevents new class registration
-        
-        RTCoverageDataPersister.dumpCoverageData (cdata, ! stopDataCollection, outFile, merge);
-    }
-    
-    public static synchronized void dumpCoverageData (File outFile, final boolean stopDataCollection)
-    {
-        outFile = outFile != null ? outFile : getCoverageOutFile ();
-        
-        ICoverageData cdata = s_cdata; // no need to use accessor
-        if (stopDataCollection) s_cdata = null; // TODO: log this NOTE: this does not really stop data collection, merely prevents new class registration
-        
-        RTCoverageDataPersister.dumpCoverageData (cdata, ! stopDataCollection, outFile, getCoverageOutMerge ());
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-    
-    
-    private RT () {} // prevent subclassing
-    
-    
-    private static File getCoverageOutFile ()
-    {
-        final IProperties appProperties = getAppProperties (); // sync accessor
-        if (appProperties != null)
-        {
-            final String property = appProperties.getProperty (EMMAProperties.PROPERTY_COVERAGE_DATA_OUT_FILE,
-                                                               EMMAProperties.DEFAULT_COVERAGE_DATA_OUT_FILE);
-            return new File (property);
-        }
-        
-        return new File (EMMAProperties.DEFAULT_COVERAGE_DATA_OUT_FILE); 
-    }
-    
-    private static boolean getCoverageOutMerge ()
-    {
-        final IProperties appProperties = getAppProperties (); // sync accessor
-        if (appProperties != null)
-        {
-            // [Boolean.toString (boolean) is J2SDK 1.4+]
-            
-            final String property = appProperties.getProperty (EMMAProperties.PROPERTY_COVERAGE_DATA_OUT_MERGE,
-                                                               EMMAProperties.DEFAULT_COVERAGE_DATA_OUT_MERGE.toString ());
-            return Property.toBoolean (property);
-        }
-        
-        return EMMAProperties.DEFAULT_COVERAGE_DATA_OUT_MERGE.booleanValue ();
-    }
-    
-        
-    private static ICoverageData s_cdata;
-    private static Runnable s_exitHook;
-    private static IProperties s_appProperties; // TODO: this is better of as java.util.Properties
-
-    private static final ExitHookManager EXIT_HOOK_MANAGER; // set in <clinit>
-    
-    private static final boolean DEBUG = false;
-    
-    static
-    {
-        if (DEBUG) System.out.println ("RT[" + System.identityHashCode (RT.class) + "]::<clinit>: loaded by " + RT.class.getClassLoader ());
-        
-        ExitHookManager temp = null;
-        try
-        {
-            temp = ExitHookManager.getSingleton ();
-        }
-        catch (Throwable t)
-        {
-            // TODO: handle better
-            t.printStackTrace (System.out);
-        }
-        EXIT_HOOK_MANAGER = temp;
-
-         
-        if (RTSettings.isStandaloneMode ())
-        {
-            if (DEBUG) System.out.println ("RT::<clinit>: STANDALONE MODE");
-            
-            // load app props, create coverage data, and register an exit hook for it:
-            reset (true, true);
-            
-            // use method-scoped loggers in RT:
-            final Logger log = Logger.getLogger ();
-            if (log.atINFO ())
-            {
-                log.info ("collecting runtime coverage data ...");
-            }
-        }
-        else
-        {
-            // load app props only:
-            reset (false, false);
-        }
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/rt/RTCoverageDataPersister.java b/core/java12/com/vladium/emma/rt/RTCoverageDataPersister.java
deleted file mode 100644
index dfc7ed6..0000000
--- a/core/java12/com/vladium/emma/rt/RTCoverageDataPersister.java
+++ /dev/null
@@ -1,78 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: RTCoverageDataPersister.java,v 1.1.2.2 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma.rt;
-
-import java.io.File;
-
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.data.DataFactory;
-import com.vladium.emma.data.ICoverageData;
-import com.vladium.logging.Logger;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2004
- */
-abstract
-class RTCoverageDataPersister
-{
-    // public: ................................................................
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    /*
-     * Stateless package-private method shared by RT and RTExitHook for coverage
-     * data persistence. This method was moved out of RT class after build 4120
-     * in order to decrease classloading dependency set for RTExitHook
-     * (FR SF978671).
-     */
-    static void dumpCoverageData (final ICoverageData cdata, final boolean useSnapshot,
-                                  final File outFile, final boolean merge)
-    {
-        try
-        {
-            if (cdata != null)
-            {
-                // use method-scoped loggers everywhere in RT:
-                final Logger log = Logger.getLogger ();
-                final boolean info = log.atINFO ();
-                
-                final long start = info ? System.currentTimeMillis () : 0;
-                {
-                    final ICoverageData cdataView = useSnapshot ? cdata.shallowCopy () : cdata;
-                    
-                    synchronized (Object.class) // fake a JVM-global critical section when multilply loaded RT's write to the same file
-                    {
-                        DataFactory.persist (cdataView, outFile, merge);
-                    }
-                }
-                if (info)
-                {
-                    final long end = System.currentTimeMillis ();
-                    
-                    log.info ("runtime coverage data " + (merge ? "merged into" : "written to") + " [" + outFile.getAbsolutePath () + "] {in " + (end - start) + " ms}");
-                }
-            }
-        }
-        catch (Throwable t)
-        {
-            // log
-            t.printStackTrace ();
-            
-            // TODO: do better chaining in JRE 1.4+
-            throw new RuntimeException (IAppConstants.APP_NAME + " failed to dump coverage data: " + t.toString ());
-        }
-    }
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/rt/RTExitHook.java b/core/java12/com/vladium/emma/rt/RTExitHook.java
deleted file mode 100644
index 56b6d10..0000000
--- a/core/java12/com/vladium/emma/rt/RTExitHook.java
+++ /dev/null
@@ -1,126 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: RTExitHook.java,v 1.1.1.1.2.2 2004/07/10 03:34:53 vlad_r Exp $
- */
-package com.vladium.emma.rt;
-
-import java.io.File;
-import java.io.IOException;
-import java.io.InputStream;
-import java.util.Properties;
-import java.util.StringTokenizer;
-
-import com.vladium.emma.data.ICoverageData;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-final class RTExitHook implements Runnable
-{
-    // public: ................................................................
-    
-    
-    public synchronized void run ()
-    {
-        if (m_cdata != null)
-        {
-            RTCoverageDataPersister.dumpCoverageData (m_cdata, true, m_outFile, m_merge);
-            
-            m_RT = null;
-            m_cdata = null;
-        }
-    }
-    
-    public static void createClassLoaderClosure ()
-    {
-        Properties closureMap = null;
-        
-        InputStream in = null;
-        try
-        {
-            // note that this does not use ClassLoaderResolver by design
-            // (closure loading must not load any app classes that are outside
-            /// the closure list)
-            
-            in = RTExitHook.class.getResourceAsStream (CLOSURE_RESOURCE);
-            if (in != null)
-            {
-                closureMap = new Properties ();
-                closureMap.load (in);
-            }
-            else
-            {
-                throw new Error ("packaging failure: closure resource not found");
-            }
-        }
-        catch (Exception e)
-        {
-            e.printStackTrace (System.out);
-            
-            throw new Error ("packaging failure: " + e.toString ());
-        }
-        finally
-        {
-            if (in != null) try { in.close (); } catch (IOException ignore) { ignore.printStackTrace (); }
-        }
-        in = null;
-        
-        final String closureList = closureMap.getProperty ("closure");
-        if (closureList == null)
-        {
-            throw new Error ("packaging failure: no closure mapping");
-        }
-        
-        // note that this uses the current classloader (only), consistently
-        // with the getResourceAsStream() above:
-        
-        final ClassLoader loader = RTExitHook.class.getClassLoader ();
-        
-        final StringTokenizer tokenizer = new StringTokenizer (closureList, ",");
-        while (tokenizer.hasMoreTokens ())
-        {
-            final String className = tokenizer.nextToken ();
-            
-            try
-            {
-                Class.forName (className, true, loader);
-            }
-            catch (Exception e)
-            {
-                throw new Error ("packaging failure: class [" + className + "] not found {" + e.toString () + "}");
-            }
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    RTExitHook (final Class RT, final ICoverageData cdata, final File outFile, final boolean merge)
-    {
-        m_RT = RT;
-        m_cdata = cdata;
-        
-        m_outFile = outFile;
-        m_merge = merge;
-    }
-        
-    // private: ...............................................................
-
-
-    private final File m_outFile;
-    private final boolean m_merge;
-    
-    private Class m_RT; // keep our RT class pinned in memory
-    private ICoverageData m_cdata;
-    
-    private static final String CLOSURE_RESOURCE = "RTExitHook.closure"; // relative to this package
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/rt/RTSettings.java b/core/java12/com/vladium/emma/rt/RTSettings.java
deleted file mode 100644
index 8b37f53..0000000
--- a/core/java12/com/vladium/emma/rt/RTSettings.java
+++ /dev/null
@@ -1,46 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: RTSettings.java,v 1.1.1.1 2004/05/09 16:57:44 vlad_r Exp $
- */
-package com.vladium.emma.rt;
-
-// ----------------------------------------------------------------------------
-/**
- * Conceptually, this class is an extention of class RT. This is a separate class,
- * however, to help load RT in a lazy manner.
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class RTSettings
-{
-    // public: ................................................................
-    
-    
-    public static synchronized boolean isStandaloneMode ()
-    {
-        return ! s_not_standalone;
-    }
-    
-    public static synchronized void setStandaloneMode (final boolean standalone)
-    {
-        s_not_standalone = ! standalone;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private RTSettings () {} // prevent subclassing
-        
-    private static boolean s_not_standalone;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/emma/runCommand.java b/core/java12/com/vladium/emma/runCommand.java
deleted file mode 100644
index 88ffe8f..0000000
--- a/core/java12/com/vladium/emma/runCommand.java
+++ /dev/null
@@ -1,332 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: runCommand.java,v 1.1.1.1.2.1 2004/07/16 23:32:03 vlad_r Exp $
- */
-package com.vladium.emma;
-
-import java.io.File;
-import java.io.IOException;
-import java.util.jar.Attributes;
-import java.util.jar.JarFile;
-import java.util.jar.Manifest;
-
-import com.vladium.util.ClassLoaderResolver;
-import com.vladium.util.Strings;
-import com.vladium.util.args.IOptsParser;
-import com.vladium.util.asserts.$assert;
-import com.vladium.emma.rt.AppRunner;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class runCommand extends Command
-{
-    // public: ................................................................
-
-
-    public synchronized void run ()
-    {
-        ClassLoader loader;
-        try
-        {
-            loader = ClassLoaderResolver.getClassLoader ();
-        }
-        catch (Throwable t)
-        {
-            loader = getClass ().getClassLoader ();
-        }
-        
-        try
-        {
-            // process 'args':
-            {
-                final IOptsParser parser = getOptParser (loader);
-                final IOptsParser.IOpts parsedopts = parser.parse (m_args);
-                
-                // check if usage is requested before checking args parse errors etc:
-                {
-                    final int usageRequestLevel = parsedopts.usageRequestLevel ();
-
-                    if (usageRequestLevel > 0)
-                    {
-                        usageexit (parser, usageRequestLevel, null);
-                        return;
-                    }
-                }
-                
-                final IOptsParser.IOpt [] opts = parsedopts.getOpts ();
-                
-                if (opts == null) // this means there were args parsing errors
-                {
-                    parsedopts.error (m_out, STDOUT_WIDTH);
-                    usageexit (parser, IOptsParser.SHORT_USAGE, null);
-                    return;
-                }
-                
-                // process parsed args:
-                try
-                {
-                    for (int o = 0; o < opts.length; ++ o)
-                    {
-                        final IOptsParser.IOpt opt = opts [o];
-                        final String on = opt.getCanonicalName ();
-                        
-                        if (! processOpt (opt))
-                        {
-                            if ("cp".equals (on))
-                            {
-                                m_classpath = getListOptValue (opt, PATH_DELIMITERS, true);
-                            }
-                            else if ("jar".equals (on))
-                            {
-                                m_jarMode = true;
-                            }
-                            else if ("f".equals (on))
-                            {
-                                m_scanCoveragePath = getOptionalBooleanOptValue (opt);
-                            }
-                            else if ("sp".equals (on))
-                            {
-                                m_srcpath = getListOptValue (opt, PATH_DELIMITERS, true);
-                            }
-                            else if ("raw".equals (on))
-                            {
-                                m_dumpRawData = getOptionalBooleanOptValue (opt); 
-                            }
-                            else if ("out".equals (on))
-                            {
-                                m_outFileName = opt.getFirstValue ();
-                            }
-                            else if ("merge".equals (on))
-                            {
-                                m_outDataMerge = getOptionalBooleanOptValue (opt) ? Boolean.TRUE : Boolean.FALSE; 
-                            }
-                            else if ("r".equals (on))
-                            {
-                                m_reportTypes = Strings.merge (opt.getValues (), COMMA_DELIMITERS, true);
-                            }
-                            else if ("ix".equals (on))
-                            {
-                                m_ixpath = getListOptValue (opt, COMMA_DELIMITERS, true);
-                            }
-                        }
-                    }
-                    
-                    // user '-props' file property overrides:
-                    
-                    if (! processFilePropertyOverrides ()) return;
-                    
-                    // process prefixed opts:
-                    
-                    processCmdPropertyOverrides (parsedopts);
-                }
-                catch (IOException ioe)
-                {
-                    throw new EMMARuntimeException (IAppErrorCodes.ARGS_IO_FAILURE, ioe);
-                }
-                
-                
-                // process free args:
-                {
-                    final String [] freeArgs = parsedopts.getFreeArgs ();
-                    
-                    if (m_jarMode)
-                    {
-                        if ((freeArgs == null) || (freeArgs.length == 0))
-                        {
-                            usageexit (parser, IOptsParser.SHORT_USAGE, "missing jar file name");
-                            return;
-                        }
-                        
-                        if ($assert.ENABLED) $assert.ASSERT (freeArgs != null && freeArgs.length > 0, "invalid freeArgs");
-    
-                        final File jarfile = new File (freeArgs [0]);
-                        final String jarMainClass;
-                        try
-                        {
-                            jarMainClass = openJarFile (jarfile); // the rest of free args are *not* ignored
-                        }
-                        catch (IOException ioe)
-                        {
-                            // TODO: is the right error code?
-                            throw new EMMARuntimeException (IAppErrorCodes.ARGS_IO_FAILURE, ioe);
-                        }                    
-                        
-                        if (jarMainClass == null)
-                        {
-                            exit (true, "failed to load Main-Class manifest attribute from [" + jarfile.getAbsolutePath () + "]", null, RC_UNEXPECTED);
-                            return; 
-                        }
-                        
-                        if ($assert.ENABLED) $assert.ASSERT (jarMainClass != null, "invalid jarMainClass");
-                        
-                        m_appArgs = new String [freeArgs.length];
-                        System.arraycopy (freeArgs, 1, m_appArgs, 1, freeArgs.length - 1);
-                        m_appArgs [0] = jarMainClass;
-                        
-                        m_classpath = new String [] { jarfile.getPath () };
-                    }
-                    else
-                    {
-                        if ((freeArgs == null) || (freeArgs.length == 0))
-                        {
-                            usageexit (parser, IOptsParser.SHORT_USAGE, "missing application class name");
-                            return;
-                        }
-                        
-                        m_appArgs = freeArgs;
-                    }
-                }
-                // [m_appArgs: { mainclass, arg1, arg2, ... }]
-
-                
-                // handle cmd line-level defaults and option interaction
-                {
-                    if (DEFAULT_TO_SYSTEM_CLASSPATH)
-                    {
-                        if (m_classpath == null)
-                        {
-                            // TODO" this is not guaranteed to work (in WebStart etc), so double check if I should remove this
-                            
-                            final String systemClasspath = System.getProperty ("java.class.path", "");
-                            if (systemClasspath.length () == 0)
-                            {
-                                // TODO: assume "." just like Sun JVMs in this case?
-                                usageexit (parser, IOptsParser.SHORT_USAGE, "could not infer coverage classpath from 'java.class.path'; use an explicit -cp option");
-                                return;
-                            }
-                            
-                            m_classpath = new String [] {systemClasspath};
-                        }
-                    }
-                    else
-                    {
-                        if (m_classpath == null)
-                        {
-                            usageexit (parser, IOptsParser.SHORT_USAGE, "either '-cp' or '-jar' option is required");
-                            return;
-                        }
-                    }               
-
-                    // TODO: who owns setting this 'txt' default? most likely AppRunner
-                    if (m_reportTypes == null)
-                    {
-                        m_reportTypes = new String [] {"txt"};
-                    }
-                }
-            }
-            
-            // run the app:
-            {
-                if ($assert.ENABLED) $assert.ASSERT (m_appArgs != null && m_appArgs.length > 0, "invalid m_appArgs");
-                
-                final String [] appargs = new String [m_appArgs.length - 1];
-                System.arraycopy (m_appArgs, 1, appargs, 0, appargs.length);
-                
-                final AppRunner processor = AppRunner.create (loader);
-                processor.setAppName (IAppConstants.APP_NAME); // for log prefixing
-                
-                processor.setAppClass (m_appArgs [0], appargs);
-                processor.setCoveragePath (m_classpath, true); // TODO: an option to set 'canonical'?
-                processor.setScanCoveragePath (m_scanCoveragePath);
-                processor.setSourcePath (m_srcpath);
-                processor.setInclExclFilter (m_ixpath);
-                processor.setDumpSessionData (m_dumpRawData);
-                processor.setSessionOutFile (m_outFileName);
-                processor.setSessionOutMerge (m_outDataMerge);
-                if ($assert.ENABLED) $assert.ASSERT (m_reportTypes != null, "m_reportTypes no set");
-                processor.setReportTypes (m_reportTypes);
-                processor.setPropertyOverrides (m_propertyOverrides);
-                
-                processor.run ();
-            }
-        }
-        catch (EMMARuntimeException yre)
-        {
-            // TODO: see below
-            
-            exit (true, yre.getMessage (), yre, RC_UNEXPECTED); // does not return
-            return;
-        }
-        catch (Throwable t)
-        {
-            // TODO: embed: OS/JVM fingerprint, build #, etc
-            // TODO: save stack trace in a file and prompt user to send it to ...
-            
-            exit (true, "unexpected failure: ", t, RC_UNEXPECTED); // does not return
-            return;
-        }
-
-        exit (false, null, null, RC_OK);
-    }
-    
-    // protected: .............................................................
-
-
-    protected runCommand (final String usageToolName, final String [] args)
-    {
-        super (usageToolName, args);
-    }
-
-    protected void initialize ()
-    {
-        // TODO: clean up instance state
-        
-        super.initialize ();
-    }
-    
-    protected String usageArgsMsg ()
-    {
-        return "[options] class [args...] | -jar [options] jarfile [args...]";
-    }
-    
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static String openJarFile (final File file)
-        throws IOException
-    {
-        JarFile jarfile = null;
-        try
-        {
-            jarfile = new JarFile (file, false);
-            
-            final Manifest manifest = jarfile.getManifest ();
-            if (manifest == null) return null;
-            
-            final Attributes attributes = manifest.getMainAttributes ();
-            if (attributes == null) return null;
-
-            final String jarMainClass = attributes.getValue (Attributes.Name.MAIN_CLASS);
-            
-            return jarMainClass;
-        }
-        finally
-        {
-            if (jarfile != null) try { jarfile.close (); } catch (IOException ignore) {}
-        }
-    }
-        
-        
-    private String [] m_classpath, m_srcpath;
-    private boolean m_jarMode;
-    private boolean m_scanCoveragePath; // defaults to false
-    private String [] m_ixpath;
-    private String [] m_appArgs;
-    private boolean m_dumpRawData; // defaults to false
-    private String m_outFileName;
-    private Boolean m_outDataMerge; 
-    private String [] m_reportTypes;
-    
-    private static final boolean DEFAULT_TO_SYSTEM_CLASSPATH = false;
-        
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/jcd/cls/AbstractClassDefVisitor.java b/core/java12/com/vladium/jcd/cls/AbstractClassDefVisitor.java
deleted file mode 100644
index 4b429ac..0000000
--- a/core/java12/com/vladium/jcd/cls/AbstractClassDefVisitor.java
+++ /dev/null
@@ -1,65 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AbstractClassDefVisitor.java,v 1.1.1.1 2004/05/09 16:57:44 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-abstract class AbstractClassDefVisitor implements IClassDefVisitor
-{
-    // public: ................................................................
-
-    // IClassDefVisitor:
-
-    public Object visit (final ClassDef cls, final Object ctx)
-    {
-        visit (cls.getConstants (), ctx);
-        visit (cls.getInterfaces (), ctx);
-        visit (cls.getFields (), ctx);
-        visit (cls.getMethods (), ctx);
-        visit (cls.getAttributes (), ctx);
-        
-        return ctx;
-    }
-
-    public Object visit (final IAttributeCollection attributes, final Object ctx)
-    {
-        return ctx;
-    }
-
-    public Object visit (final IConstantCollection constants, final Object ctx)
-    {
-        return ctx;
-    }
-
-    public Object visit (final IFieldCollection fields, final Object ctx)
-    {
-        return ctx;
-    }
-
-    public Object visit (final IInterfaceCollection interfaces, final Object ctx)
-    {
-        return ctx;
-    }
-
-    public Object visit (final IMethodCollection methods, final Object ctx)
-    {
-        return ctx;
-    }
-        
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/AttributeCollection.java b/core/java12/com/vladium/jcd/cls/AttributeCollection.java
deleted file mode 100644
index ed24d3e..0000000
--- a/core/java12/com/vladium/jcd/cls/AttributeCollection.java
+++ /dev/null
@@ -1,217 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AttributeCollection.java,v 1.1.1.1 2004/05/09 16:57:44 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
-import com.vladium.jcd.cls.attribute.*;
-import com.vladium.jcd.lib.UDataOutputStream;
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-final class AttributeCollection implements IAttributeCollection
-{
-    // public: ................................................................
-    
-    // TODO: extend ItemCollection into all XXXCollection classes ?
-    
-
-    // ACCESSORS:
-        
-    public final Attribute_info get (final int offset)
-    {
-        return (Attribute_info) m_attributes.get (offset);
-    }
-    
-    public final boolean hasSynthetic ()
-    {
-        return m_syntheticRefCount > 0;
-    }
-    
-    public final boolean hasBridge ()
-    {
-        return m_bridgeRefCount > 0;
-    }
-    
-    public final InnerClassesAttribute_info getInnerClassesAttribute ()
-    {
-        final int innerClassesAttributeOffset = m_innerClassesAttributeOffset;
-        if (innerClassesAttributeOffset < 0)
-            return null;
-        else
-            return (InnerClassesAttribute_info) get (innerClassesAttributeOffset);
-    }
-    
-    public final int size ()
-    {
-        return m_attributes.size (); 
-    }
-    
-    public final long length ()
-    {
-        // TODO: cache?
-        
-        long result = 2;
-        
-        int _attributes_count = m_attributes.size (); // use size() if this class becomes non-final
-        for (int i = 0; i < _attributes_count; i++) result += get (i).length ();
-        
-        return result;
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final AttributeCollection _clone = (AttributeCollection) super.clone ();
-            
-            // deep clone:
-            
-            final int attributes_count = m_attributes.size (); // use size() if this class becomes non-final
-            _clone.m_attributes = new ArrayList (attributes_count);
-            for (int a = 0; a < attributes_count; ++ a)
-            {
-                _clone.m_attributes.add (((Attribute_info) m_attributes.get (a)).clone ());
-            }
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }        
-    }
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        int attributes_count = size ();
-        out.writeU2 (attributes_count);
-        
-        for (int i = 0; i < attributes_count; i++)
-        {
-            get (i).writeInClassFormat (out);
-        }
-    }
-
-    // Visitor:
-    
-    public void accept (final IClassDefVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-
-
-    // MUTATORS:
-
-    public int add (final Attribute_info attribute)
-    {
-        final List/* Attribute_info */ attributes = m_attributes;
-        
-        final int result = attributes.size ();
-        attributes.add (attribute);
-        
-        if (attribute instanceof SyntheticAttribute_info)
-            ++ m_syntheticRefCount;
-        else if (attribute instanceof InnerClassesAttribute_info)
-        {
-            if (m_innerClassesAttributeOffset >= 0)
-                throw new IllegalArgumentException ("this attribute collection already has an InnerClasses attribute");
-            
-            m_innerClassesAttributeOffset = result;
-        }
-        else if (attribute instanceof BridgeAttribute_info)
-            ++ m_bridgeRefCount;
-            
-        if (DISALLOW_MULTIPLE_SYNTHETIC_ATTRIBUTES && $assert.ENABLED)
-            $assert.ASSERT (m_syntheticRefCount >= 0 && m_syntheticRefCount <= 1,
-            "bad synthetic attribute count: " + m_syntheticRefCount);
-        
-        return result;
-    }
-    
-    public Attribute_info set (final int offset, final Attribute_info attribute)
-    {
-        final Attribute_info result = (Attribute_info) m_attributes.set (offset, attribute);
-         
-        if (result instanceof SyntheticAttribute_info)
-            -- m_syntheticRefCount;
-        else if (result instanceof InnerClassesAttribute_info)
-            m_innerClassesAttributeOffset = -1;
-        else if (result instanceof BridgeAttribute_info)
-            -- m_bridgeRefCount;
-            
-        if (attribute instanceof SyntheticAttribute_info)
-            ++ m_syntheticRefCount;
-        else if (attribute instanceof InnerClassesAttribute_info)
-            m_innerClassesAttributeOffset = offset;
-        else if (attribute instanceof BridgeAttribute_info)
-            ++ m_bridgeRefCount;
-            
-        if (DISALLOW_MULTIPLE_SYNTHETIC_ATTRIBUTES && $assert.ENABLED)
-            $assert.ASSERT (m_syntheticRefCount >= 0 && m_syntheticRefCount <= 1,
-            "bad synthetic attribute count: " + m_syntheticRefCount);
-            
-        return result; 
-    }
-    
-    public Attribute_info remove (final int offset)
-    {
-        final Attribute_info result = (Attribute_info) m_attributes.remove (offset);
-        
-        if (result instanceof SyntheticAttribute_info)
-            -- m_syntheticRefCount;
-        else if (result instanceof InnerClassesAttribute_info)
-            m_innerClassesAttributeOffset = -1;
-        else if (result instanceof BridgeAttribute_info)
-            -- m_bridgeRefCount;
-            
-        if (DISALLOW_MULTIPLE_SYNTHETIC_ATTRIBUTES && $assert.ENABLED)
-            $assert.ASSERT (m_syntheticRefCount >= 0 && m_syntheticRefCount <= 1,
-            "bad synthetic attribute count: " + m_syntheticRefCount);
-            
-        return result;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    AttributeCollection (final int capacity)
-    {
-        m_attributes = capacity < 0 ? new ArrayList () : new ArrayList (capacity);
-        m_innerClassesAttributeOffset = -1;
-    }
-
-    // private: ...............................................................
-
-    
-    private List/* Attribute_info */ m_attributes; // never null
-    private transient int m_syntheticRefCount, m_bridgeRefCount;
-    private transient int m_innerClassesAttributeOffset;
-    
-    // note: the spec does not disallow multiple synthetic attributes
-    private static final boolean DISALLOW_MULTIPLE_SYNTHETIC_ATTRIBUTES = false;
-    
-    // note: the spec disallows multiple inner classes attributes
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/ClassDef.java b/core/java12/com/vladium/jcd/cls/ClassDef.java
deleted file mode 100644
index bf26257..0000000
--- a/core/java12/com/vladium/jcd/cls/ClassDef.java
+++ /dev/null
@@ -1,732 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ClassDef.java,v 1.1.1.1.2.1 2004/07/16 23:32:30 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import java.io.DataOutputStream;
-import java.io.IOException;
-import java.security.MessageDigest;
-import java.security.NoSuchAlgorithmException;
-import java.util.Arrays;
-
-import com.vladium.jcd.cls.attribute.AttributeElementFactory;
-import com.vladium.jcd.cls.attribute.Attribute_info;
-import com.vladium.jcd.cls.attribute.CodeAttribute_info;
-import com.vladium.jcd.cls.attribute.InnerClassesAttribute_info;
-import com.vladium.jcd.cls.constant.CONSTANT_Class_info;
-import com.vladium.jcd.cls.constant.CONSTANT_Fieldref_info;
-import com.vladium.jcd.cls.constant.CONSTANT_NameAndType_info;
-import com.vladium.jcd.cls.constant.CONSTANT_String_info;
-import com.vladium.jcd.cls.constant.CONSTANT_Utf8_info;
-import com.vladium.jcd.compiler.IClassFormatOutput;
-import com.vladium.jcd.lib.Types;
-import com.vladium.jcd.lib.UDataOutputStream;
-import com.vladium.util.ByteArrayOStream;
-
-// ----------------------------------------------------------------------------
-/**
- * This class represents the abstract syntax table (AST) that {@link com.vladium.jcd.parser.ClassDefParser}
- * produces from bytecode. Most elements are either settable or extendible.
- * This class also implements {@link com.vladium.jcd.compiler.IClassFormatOutput}
- * and works with {@link com.vladium.jcd.compiler.ClassWriter} to produce
- * bytecode without an external compiler.<P>
- * 
- * MT-safety: this class and all interfaces used by it are not safe for
- * access from multiple concurrent threads. 
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class ClassDef implements Cloneable, IAccessFlags, IClassFormatOutput
-{
-    // public: ................................................................
-
-
-    public ClassDef ()
-    {
-        m_version = new int [2];
-
-        m_constants = ElementFactory.newConstantCollection (-1);
-        m_interfaces = ElementFactory.newInterfaceCollection (-1);
-        m_fields = ElementFactory.newFieldCollection (-1);
-        m_methods = ElementFactory.newMethodCollection (-1);
-        m_attributes = ElementFactory.newAttributeCollection (-1);
-    }
-    
-    // Visitor:
-    
-    public void accept (final IClassDefVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-
-
-    public long getMagic ()
-    {
-        return m_magic;
-    }
-    
-    public void setMagic (final long magic)
-    {
-        m_magic = magic;
-    }
-    
-    
-    public int [] getVersion ()
-    {
-        return m_version;
-    }
-    
-    public void setVersion (final int [] version)
-    {
-        m_version [0] = version [0];
-        m_version [1] = version [1];
-    }
-    
-    public final void setDeclaredSUID (final long suid)
-    {
-        m_declaredSUID = suid;
-    }
-    
-
-    public int getThisClassIndex ()
-    {
-        return m_this_class_index;
-    }
-    
-    public void setThisClassIndex (final int this_class_index)
-    {
-        m_this_class_index = this_class_index;
-    }
-    
-    public CONSTANT_Class_info getThisClass ()
-    {
-        return (CONSTANT_Class_info) m_constants.get (m_this_class_index);
-    }
-    
-    public CONSTANT_Class_info getSuperClass ()
-    {
-        return (CONSTANT_Class_info) m_constants.get (m_super_class_index);
-    }
-    
-    public String getName ()
-    {
-        return getThisClass ().getName (this);
-    }
-
-
-    public int getSuperClassIndex ()
-    {
-        return m_super_class_index;
-    }
-    
-    public void setSuperClassIndex (final int super_class_index)
-    {
-        m_super_class_index = super_class_index;
-    }
-    
-    // IAccessFlags:
-
-    public final int getAccessFlags ()
-    {
-        return m_access_flags;
-    }
-
-    public final void setAccessFlags (final int flags)
-    {
-        m_access_flags = flags;
-    }
-    
-    public boolean isInterface ()
-    {
-        return (m_access_flags & ACC_INTERFACE) != 0;
-    }
-    
-    public boolean isSynthetic ()
-    {
-        return m_attributes.hasSynthetic ();
-    }
-    
-    public boolean isNested (final int [] nestedAccessFlags)
-    {
-        final InnerClassesAttribute_info innerClassesAttribute = m_attributes.getInnerClassesAttribute ();
-        
-        if (innerClassesAttribute == null)
-            return false;
-        else
-            return innerClassesAttribute.makesClassNested (m_this_class_index, nestedAccessFlags);
-    }
-    
-    // methods for getting various nested tables:
-    
-    public IConstantCollection getConstants ()
-    {
-        return m_constants;
-    }
-    
-    public IInterfaceCollection getInterfaces ()
-    {
-        return m_interfaces;
-    }
-    
-    public IFieldCollection getFields ()
-    {
-        return m_fields;
-    }
-    
-    public IMethodCollection getMethods ()
-    {
-        return m_methods;
-    }
-    
-    public IAttributeCollection getAttributes ()
-    {
-        return m_attributes;
-    }
-    
-    public int [] getFields (final String name)
-    {
-        return m_fields.get (this, name);
-    }
-    
-    public int [] getMethods (final String name)
-    {
-        return m_methods.get (this, name);
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final ClassDef _clone = (ClassDef) super.clone ();
-            
-            // do deep copy:
-            _clone.m_version = (int []) m_version.clone ();
-            _clone.m_constants = (IConstantCollection) m_constants.clone ();
-            _clone.m_interfaces = (IInterfaceCollection) m_interfaces.clone ();
-            _clone.m_fields = (IFieldCollection) m_fields.clone ();
-            _clone.m_methods = (IMethodCollection) m_methods.clone ();
-            _clone.m_attributes = (IAttributeCollection) m_attributes.clone ();
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }
-    }
-    
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        if (out == null) throw new IllegalArgumentException ("null input: out");
-        
-        out.writeU4 (m_magic);
-        
-        out.writeU2 (m_version [1]);
-        out.writeU2 (m_version [0]);
-        
-        m_constants.writeInClassFormat (out);
-        
-        out.writeU2 (m_access_flags);
-        
-        out.writeU2 (m_this_class_index);
-        out.writeU2 (m_super_class_index);
-        
-        m_interfaces.writeInClassFormat (out);
-        m_fields.writeInClassFormat (out);
-        m_methods.writeInClassFormat (out);
-        m_attributes.writeInClassFormat (out);
-    }
-    
-    public final long getDeclaredSUID ()
-    {
-        return m_declaredSUID;
-    }
-    
-    /**
-     * This follows the spec at http://java.sun.com/j2se/1.4.1/docs/guide/serialization/spec/class.doc6.html#4100
-     * as well as undocumented hacks used by Sun's 1.4.2 J2SDK
-     */
-    public final long computeSUID (final boolean skipCLINIT)
-    {
-        long result = m_declaredSUID;
-        if (result != 0L)
-            return result;
-        else
-        {
-            try
-            {
-                final ByteArrayOStream bout = new ByteArrayOStream (1024); // TODO: reuse these 
-                final DataOutputStream dout = new DataOutputStream (bout);
-                
-                // (1) The class name written using UTF encoding: 
-
-                dout.writeUTF (Types.vmNameToJavaName (getName ())); // [in Java format]
-                
-                // (2) The class modifiers written as a 32-bit integer:
-                
-                // ACC_STATIC is never written for nested classes/interfaces;
-                // however, ACC_SUPER must be ignored:
-                {
-                    // this is tricky: for static/non-static nested classes that
-                    // were declared protected in the source the usual access flags
-                    // will have ACC_PUBLIC set; the only way to achieve J2SDK
-                    // compatibility is to recover the source access flags
-                    // from the InnerClasses attribute:
-                    
-                    final int [] nestedAccessFlags = new int [1];
-                    
-                    final int modifiers = (isNested (nestedAccessFlags)
-                            ? nestedAccessFlags [0]
-                            : getAccessFlags ())
-                        & (ACC_PUBLIC | ACC_FINAL | ACC_INTERFACE | ACC_ABSTRACT);
-
-                    // if/when emma decides to instrument interfaces for <clinit>
-                    // coverage, compensate for javac bug in which ABSTRACT bit
-                    // was set for an interface only if the interface declared methods
-                    // [Sun's J2SDK]:
-                    
-                    dout.writeInt (modifiers);
-                }
-                
-                // not doing another J2SDK compensation for arrays, because
-                // we never load/instrument those 
-                
-                // (3) The name of each interface sorted by name written using UTF encoding
-                {
-                    final IInterfaceCollection interfaces = getInterfaces ();
-                    final String [] ifcs = new String [interfaces.size ()];
-                    
-                    final int iLimit = ifcs.length;
-                    for (int i = 0; i < iLimit; ++ i)
-                    {
-                        // [in Java format]
-                        ifcs [i] = Types.vmNameToJavaName (((CONSTANT_Class_info) m_constants.get (interfaces.get (i))).getName (this));
-                    }
-                    
-                    Arrays.sort (ifcs);
-                    for (int i = 0; i < iLimit; ++ i)
-                    {
-                        dout.writeUTF (ifcs [i]);
-                    }
-                }
-                
-                // (4) For each field of the class sorted by field name (except
-                // private static and private transient fields):
-                //      a. The name of the field in UTF encoding. 
-                //      b. The modifiers of the field written as a 32-bit integer. 
-                //      c. The descriptor of the field in UTF encoding 
-                {
-                    final IFieldCollection fields = getFields ();
-                    final FieldDescriptor [] fds = new FieldDescriptor [fields.size ()];
-                    
-                    int fcount = 0;
-                    for (int f = 0, fLimit = fds.length; f < fLimit; ++ f)
-                    {
-                        final Field_info field = fields.get (f);
-                        final int modifiers = field.getAccessFlags ();
-                        
-                        if (((modifiers & ACC_PRIVATE) == 0) ||
-                            ((modifiers & (ACC_STATIC | ACC_TRANSIENT)) == 0))
-                            fds [fcount ++] = new FieldDescriptor (field.getName (this), modifiers, field.getDescriptor (this));
-                    }
-                    
-                    if (fcount > 0)
-                    {
-                        Arrays.sort (fds, 0, fcount);
-                        for (int i = 0; i < fcount; ++ i)
-                        {
-                            final FieldDescriptor fd = fds [i];
-                            
-                            dout.writeUTF (fd.m_name);
-                            dout.writeInt (fd.m_modifiers);
-                            dout.writeUTF (fd.m_descriptor);
-                        }
-                    }
-                }
-                
-                // (5) If a class initializer exists, write out the following: 
-                //      a. The name of the method, <clinit>, in UTF encoding. 
-                //      b. The modifier of the method, ACC_STATIC, written as a 32-bit integer. 
-                //      c. The descriptor of the method, ()V, in UTF encoding. 
-                // (6) For each non-private constructor sorted by method name and signature: 
-                //      a. The name of the method, <init>, in UTF encoding. 
-                //      b. The modifiers of the method written as a 32-bit integer. 
-                //      c. The descriptor of the method in UTF encoding. 
-                // (7) For each non-private method sorted by method name and signature: 
-                //      a. The name of the method in UTF encoding. 
-                //      b. The modifiers of the method written as a 32-bit integer. 
-                //      c. The descriptor of the method in UTF encoding.
-                
-                // note: although this is not documented, J2SDK code uses '.''s as
-                // descriptor separators (this is done for methods only, not for fields)
-                {
-                    final IMethodCollection methods = getMethods ();
-                    
-                    boolean hasCLINIT = false;
-                    final ConstructorDescriptor [] cds = new ConstructorDescriptor [methods.size ()];
-                    final MethodDescriptor [] mds = new MethodDescriptor [cds.length];
-                    
-                    int ccount = 0, mcount = 0;
-                    
-                    for (int i = 0, iLimit = cds.length; i < iLimit; ++ i)
-                    {
-                        final Method_info method = methods.get (i);
-                        
-                        final String name = method.getName (this);
-                        
-                        if (! hasCLINIT && IClassDefConstants.CLINIT_NAME.equals (name))
-                        {
-                            hasCLINIT  = true;
-                            continue;
-                        }
-                        else
-                        {
-                            final int modifiers = method.getAccessFlags ();
-                            if ((modifiers & ACC_PRIVATE) == 0)
-                            {
-                                if (IClassDefConstants.INIT_NAME.equals (name))
-                                    cds [ccount ++] = new ConstructorDescriptor (modifiers, method.getDescriptor (this));
-                                else
-                                    mds [mcount ++] = new MethodDescriptor (name, modifiers, method.getDescriptor (this));
-                            }
-                        }
-                    }
-                    
-                    if (hasCLINIT && ! skipCLINIT)
-                    {
-                        dout.writeUTF (IClassDefConstants.CLINIT_NAME);
-                        dout.writeInt (ACC_STATIC);
-                        dout.writeUTF (IClassDefConstants.CLINIT_DESCRIPTOR);
-                    }
-                    
-                    if (ccount > 0)
-                    {
-                        Arrays.sort (cds, 0, ccount);
-                        
-                        for (int i = 0; i < ccount; ++ i)
-                        {
-                            final ConstructorDescriptor cd = cds [i];
-                        
-                            dout.writeUTF (IClassDefConstants.INIT_NAME);
-                            dout.writeInt (cd.m_modifiers);
-                            dout.writeUTF (cd.m_descriptor.replace ('/', '.'));
-                        }
-                    }
-                    
-                    if (mcount > 0)
-                    {
-                        Arrays.sort (mds, 0, mcount);
-                        
-                        for (int i = 0; i < mcount; ++ i)
-                        {
-                            final MethodDescriptor md = mds [i];
-                        
-                            dout.writeUTF (md.m_name);
-                            dout.writeInt (md.m_modifiers);
-                            dout.writeUTF (md.m_descriptor.replace ('/', '.'));
-                        }
-                    }
-                }
-        
-                dout.flush();
-                
-                
-                if (DEBUG_SUID)
-                {
-                    byte [] dump = bout.copyByteArray ();
-                    for (int x = 0; x < dump.length; ++ x)
-                    {
-                        System.out.println ("DUMP[" + x + "] = " + dump [x] + "\t" + (char) dump[x]);
-                    }
-                }
-                
-                final MessageDigest md = MessageDigest.getInstance ("SHA");
-                
-                md.update (bout.getByteArray (), 0, bout.size ());
-                final byte [] hash = md.digest ();
-
-                if (DEBUG_SUID)
-                {                    
-                    for (int x = 0; x < hash.length; ++ x)
-                    {
-                        System.out.println ("HASH[" + x + "] = " + hash [x]);
-                    }
-                }
-                
-//                    final int hash0 = hash [0];
-//                    final int hash1 = hash [1];
-//                    result = ((hash0 >>> 24) & 0xFF) | ((hash0 >>> 16) & 0xFF) << 8 | ((hash0 >>> 8) & 0xFF) << 16 | ((hash0 >>> 0) & 0xFF) << 24 |
-//                             ((hash1 >>> 24) & 0xFF) << 32 | ((hash1 >>> 16) & 0xFF) << 40 | ((hash1 >>> 8) & 0xFF) << 48 | ((hash1 >>> 0) & 0xFF) << 56;
-
-                for (int i = Math.min (hash.length, 8) - 1; i >= 0; -- i)
-                {
-                    result = (result << 8) | (hash [i] & 0xFF);
-                }
-                
-                return result;
-            }
-            catch (IOException ioe)
-            {
-                throw new Error (ioe.getMessage ());
-            }
-            catch (NoSuchAlgorithmException nsae)
-            {
-                throw new SecurityException (nsae.getMessage());
-            }
-        }
-    }
-    
-    
-    public int addCONSTANT_Utf8 (final String value, final boolean keepUnique)
-    {
-        if (keepUnique)
-        {
-            final int existing = m_constants.findCONSTANT_Utf8 (value);
-            if (existing > 0)
-            {
-                return existing;
-            }
-                
-            // [else fall through]
-        }
-
-        return m_constants.add (new CONSTANT_Utf8_info (value));
-    }
-    
-    public int addStringConstant (final String value)
-    {
-        final int value_index = addCONSTANT_Utf8 (value, true);
-        
-        // TODO: const uniqueness
-        return m_constants.add (new CONSTANT_String_info (value_index));
-    }
-    
-    public int addNameType (final String name, final String typeDescriptor)
-    {
-        final int name_index = addCONSTANT_Utf8 (name, true);
-        final int descriptor_index = addCONSTANT_Utf8 (typeDescriptor, true);
-        
-        return m_constants.add (new CONSTANT_NameAndType_info (name_index, descriptor_index));
-    }
-
-
-    public int addClassref (final String classJVMName)
-    {
-        final int name_index = addCONSTANT_Utf8 (classJVMName, true);
-        // TODO: this should do uniqueness checking:
-        
-        return m_constants.add (new CONSTANT_Class_info (name_index));
-    }
-
-    
-    /**
-     * Adds a new declared field to this class [with no attributes]
-     */
-    public int addField (final String name, final String descriptor, final int access_flags)
-    {
-        // TODO: support Fields with initializer attributes?
-        // TODO: no "already exists" check done here
-        
-        final int name_index = addCONSTANT_Utf8 (name, true);
-        final int descriptor_index = addCONSTANT_Utf8 (descriptor, true);
-        
-        final Field_info field = new Field_info (access_flags, name_index, descriptor_index,
-            ElementFactory.newAttributeCollection (0));
-        
-        return m_fields.add (field);
-    }
-    
-    /**
-     * Adds a new declared field to this class [with given attributes]
-     */
-    public int addField (final String name, final String descriptor, final int access_flags,
-                         final IAttributeCollection attributes)
-    {
-        // TODO: support Fields with initializer attributes?
-        // TODO: no "already exists" check done here
-        
-        final int name_index = addCONSTANT_Utf8 (name, true);
-        final int descriptor_index = addCONSTANT_Utf8 (descriptor, true);
-        
-        final Field_info field = new Field_info (access_flags, name_index, descriptor_index, attributes);
-        
-        return m_fields.add (field);
-    }
-
-    
-    // TODO: rework this API
-    
-    public Method_info newEmptyMethod (final String name, final String descriptor, final int access_flags)
-    {
-        // TODO: flag for making synthetic etc
-        final int attribute_name_index = addCONSTANT_Utf8 (Attribute_info.ATTRIBUTE_CODE, true);
-        final int name_index = addCONSTANT_Utf8 (name, true);
-        final int descriptor_index = addCONSTANT_Utf8 (descriptor, true);
-        
-        final IAttributeCollection attributes = ElementFactory.newAttributeCollection (0);
-        final CodeAttribute_info code = new CodeAttribute_info (attribute_name_index, 0, 0,
-            CodeAttribute_info.EMPTY_BYTE_ARRAY,
-            AttributeElementFactory.newExceptionHandlerTable (0),
-            ElementFactory.newAttributeCollection (0));
-            
-        attributes.add (code);
-        
-        final Method_info method = new Method_info (access_flags, name_index, descriptor_index, attributes);
-        
-        return method;
-    }
-    
-    public int addMethod (final Method_info method)
-    {
-        return m_methods.add (method);
-    }
-    
-    /**
-     * Adds a reference to a field declared by this class.
-     * 
-     * @return constant pool index of the reference
-     */
-    public int addFieldref (final Field_info field)
-    {
-        // TODO: keepUnique flag
-        
-        final CONSTANT_NameAndType_info nametype = new CONSTANT_NameAndType_info (field.m_name_index, field.m_descriptor_index);
-        final int nametype_index = m_constants.add (nametype); // TODO: unique logic
-        
-        return m_constants.add (new CONSTANT_Fieldref_info (m_this_class_index, nametype_index));
-    }
-    
-    /**
-     * Adds a reference to a field declared by this class.
-     * 
-     * @return constant pool index of the reference
-     */
-    public int addFieldref (final int offset)
-    {
-        // TODO: keepUnique flag
-        
-        final Field_info field = m_fields.get (offset); 
-        
-        final CONSTANT_NameAndType_info nametype = new CONSTANT_NameAndType_info (field.m_name_index, field.m_descriptor_index);
-        final int nametype_index = m_constants.add (nametype); // TODO: unique logic
-        
-        return m_constants.add (new CONSTANT_Fieldref_info (m_this_class_index, nametype_index));
-    }
-    
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-    
-    
-    private static final class FieldDescriptor implements Comparable
-    {
-        // Comparable:
-        
-        public final int compareTo (final Object obj)
-        {
-            return m_name.compareTo (((FieldDescriptor) obj).m_name);
-        }
-
-        FieldDescriptor (final String name, final int modifiers, final String descriptor)
-        {
-            m_name = name;
-            m_modifiers = modifiers;
-            m_descriptor = descriptor;
-        }
-
-        
-        final String m_name;
-        final int m_modifiers;
-        final String m_descriptor; 
-        
-    } // end of nested class
-    
-    
-    private static final class ConstructorDescriptor implements Comparable
-    {
-        // Comparable:
-        
-        public final int compareTo (final Object obj)
-        {
-            return m_descriptor.compareTo (((ConstructorDescriptor) obj).m_descriptor);
-        }
-        
-        ConstructorDescriptor (final int modifiers, final String descriptor)
-        {
-            m_modifiers = modifiers;
-            m_descriptor = descriptor;
-        }
-        
-
-        final int m_modifiers;
-        final String m_descriptor; 
-        
-    } // end of nested class
-    
-    
-    private static final class MethodDescriptor implements Comparable
-    {
-        // Comparable:
-        
-        public final int compareTo (final Object obj)
-        {
-            final MethodDescriptor rhs = (MethodDescriptor) obj;
-            
-            int result = m_name.compareTo (rhs.m_name);
-            if (result == 0)
-                result = m_descriptor.compareTo (rhs.m_descriptor);
-            
-            return result;
-        }
-
-        MethodDescriptor (final String name, final int modifiers, final String descriptor)
-        {
-            m_name = name;
-            m_modifiers = modifiers;
-            m_descriptor = descriptor;
-        }
-
-        
-        final String m_name;
-        final int m_modifiers;
-        final String m_descriptor; 
-        
-    } // end of nested class   
-    
-
-    // TODO: final fields
-    
-    private long m_magic;
-    private int [] /* major, minor */ m_version;
-    private int m_access_flags;
-    
-    private int m_this_class_index, m_super_class_index;
-    
-    private IConstantCollection m_constants;
-    private IInterfaceCollection m_interfaces;
-    private IFieldCollection m_fields;
-    private IMethodCollection m_methods;
-    private IAttributeCollection m_attributes;
-    
-    private long m_declaredSUID;
-    
-    private static final boolean DEBUG_SUID = false;
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/ConstantCollection.java b/core/java12/com/vladium/jcd/cls/ConstantCollection.java
deleted file mode 100644
index 5831a12..0000000
--- a/core/java12/com/vladium/jcd/cls/ConstantCollection.java
+++ /dev/null
@@ -1,303 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ConstantCollection.java,v 1.1.1.1 2004/05/09 16:57:45 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
-import com.vladium.jcd.cls.constant.*;
-import com.vladium.jcd.lib.UDataOutputStream;
-import com.vladium.util.ObjectIntMap;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vladimir Roubtsov
- */
-final class ConstantCollection implements IConstantCollection
-{
-    // public: ................................................................
-
-    // IConstantCollection:
-    
-    // ACCESSORS:
-        
-    public CONSTANT_info get (final int index)
-    {
-        final Object result = m_constants.get (index - 1);
-        
-        if (result == null)
-            throw new IllegalStateException ("assertion failure: dereferencing an invalid constant pool slot " + index);
-        
-        return (CONSTANT_info) result;
-    }
-
-    public IConstantCollection.IConstantIterator iterator ()
-    {
-        return new ConstantIterator (m_constants);
-    }
-    
-    public int find (final int type, final IConstantComparator comparator)
-    {
-        if (comparator == null)
-            throw new IllegalArgumentException ("null input: comparator");
-        
-        for (int i = 0; i < m_constants.size (); ++ i)
-        {
-            final CONSTANT_info constant = (CONSTANT_info) m_constants.get (i);
-            
-            if ((constant != null) && (constant.tag () == type) && comparator.equals (constant))
-                return i /* !!! */ + 1; 
-        }
-        
-        return -1;
-    }
-    
-    public int findCONSTANT_Utf8 (final String value)
-    {
-        if (value == null)
-            throw new IllegalArgumentException ("null input: value");
-        
-        // create index lazily:
-        final ObjectIntMap index = getCONSTANT_Utf8_index ();
-        final int [] result = new int [1];
-        
-        if (index.get (value, result))
-            return result [0] /* !!! */ + 1;
-        else
-            return -1;
-    }
-    
-    public int size ()
-    {
-        return m_size;
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final ConstantCollection _clone = (ConstantCollection) super.clone ();
-            
-            // deep copy:
-            final int constants_count = m_constants.size ();
-            _clone.m_constants = new ArrayList (constants_count);
-            for (int c = 0; c < constants_count; ++ c)
-            {
-                final CONSTANT_info constant = (CONSTANT_info) m_constants.get (c);
-                _clone.m_constants.add (constant == null ? null : constant.clone ());
-            }
-            
-            // note: m_CONSTANT_Utf8_index is not cloned intentionally
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }        
-    }
-
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        final int constant_pool_count = m_constants.size (); // note: this is not the same as size()
-        out.writeU2 (constant_pool_count + /* !!! */1);
-        
-        final ConstantIterator i = new ConstantIterator (m_constants);
-        for (CONSTANT_info entry; (entry = i.nextConstant ()) != null; )
-        {
-            entry.writeInClassFormat (out);
-        }
-    }
-    
-    // Visitor:
-    
-    public void accept (final IClassDefVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    
-    // MUTATORS:
-    
-    public CONSTANT_info set (final int index, final CONSTANT_info constant)
-    {
-        final int zindex = index - 1;
-        final CONSTANT_info result = (CONSTANT_info) m_constants.get (zindex);
-        
-        if (result == null)
-            throw new IllegalStateException ("assertion failure: dereferencing an invalid constant pool slot " + index);
-            
-        if (result.width () != constant.width ())
-            throw new IllegalArgumentException ("assertion failure: can't set entry of type [" + result.getClass ().getName () + "] to an entry of type [" + result.getClass ().getName () + "] at pool slot " + index);
-        
-        m_constants.set (zindex, constant);
-        
-        // update the string index if it is in use:
-        if (m_CONSTANT_Utf8_index != null)
-        {
-            // remove the old index value if it exists and is equal to 'index':
-            if (result instanceof CONSTANT_Utf8_info)
-            {
-                final String mapKey = ((CONSTANT_Utf8_info) result).m_value;
-                final int [] out = new int [1];
-        
-                if (m_CONSTANT_Utf8_index.get (mapKey, out) && (out [0] == zindex))
-                    m_CONSTANT_Utf8_index.remove (mapKey);
-            }
-            
-            // add new index value if necessary:
-            if (constant instanceof CONSTANT_Utf8_info)
-                m_CONSTANT_Utf8_index.put (((CONSTANT_Utf8_info) constant).m_value, zindex);
-        }
-        
-        return result;
-    }
-
-    public int add (final CONSTANT_info constant)
-    {
-        m_constants.add (constant);
-        ++ m_size; 
-        final int result = m_constants.size ();
-        
-        for (int width = 1; width < constant.width (); ++ width)
-        {
-            ++ m_size;
-            m_constants.add (null); // insert padding empty slots            
-        }
-        
-        // update the string index if it is in use:
-        if ((m_CONSTANT_Utf8_index != null) && (constant instanceof CONSTANT_Utf8_info))
-            m_CONSTANT_Utf8_index.put (((CONSTANT_Utf8_info) constant).m_value, result /* !!! */ - 1);
-        
-        return result;
-    }    
-        
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-
-    ConstantCollection (final int capacity)
-    {
-        m_constants = capacity < 0 ? new ArrayList () : new ArrayList (capacity);
-    }
-
-    // private: ...............................................................
-
-    
-    private static final class ConstantIterator implements IConstantCollection.IConstantIterator
-    {
-        ConstantIterator (final List/* CONSTANT_info */ constants)
-        {
-            m_constants = constants;
-            m_next_index = 1;
-            shift ();
-        }
-        
-        
-        public int nextIndex ()
-        {
-            final int result = m_index;
-            shift ();
-            
-            return result;
-        }
-        
-        public CONSTANT_info nextConstant ()
-        {
-            final int nextIndex = nextIndex ();
-            if (nextIndex < 0)
-                return null;
-            else
-                return (CONSTANT_info) m_constants.get (nextIndex - 1);
-        }
-        
-        public CONSTANT_info set (final CONSTANT_info constant)
-        {
-            final int zindex = m_prev_index - 1;
-            final CONSTANT_info result = (CONSTANT_info) m_constants.get (zindex);
-        
-            if (result == null) // this should never happen with iterators
-                throw new IllegalStateException ("assertion failure: dereferencing an invalid constant pool slot " + m_prev_index);
-                
-            if (result.width () != constant.width ())
-                throw new IllegalArgumentException ("assertion failure: can't set entry of type [" + result.getClass ().getName () + "] to an entry of type [" + result.getClass ().getName () + "] at pool slot " + m_prev_index);
-            
-            m_constants.set (zindex, constant);
-            
-            return result;
-        }
-        
-        
-        private void shift ()
-        {
-            m_prev_index = m_index;
-            m_index = m_next_index;
-            
-            if (m_index > 0)
-            {
-                try
-                {
-                    final CONSTANT_info entry = (CONSTANT_info) m_constants.get (m_index - 1);
-
-                    m_next_index += entry.width ();
-                    if (m_next_index > m_constants.size ()) m_next_index = -1;
-                }
-                catch (IndexOutOfBoundsException ioobe) // empty collection edge case
-                {
-                    m_index = m_next_index = -1;
-                }
-            }
-        }
-        
-        
-        private int m_index, m_prev_index, m_next_index;
-        private List/* CONSTANT_info */ m_constants;
-        
-    } // end of nested class
-    
-    
-    private ObjectIntMap getCONSTANT_Utf8_index ()
-    {
-        if (m_CONSTANT_Utf8_index == null)
-        {
-            final ObjectIntMap index = new ObjectIntMap (m_size);
-            
-            for (int i = 0; i < m_constants.size (); ++ i)
-            {
-                final CONSTANT_info constant = (CONSTANT_info) m_constants.get (i);
-                
-                if ((constant != null) && (constant.tag () == CONSTANT_Utf8_info.TAG))
-                {
-                    // it's ok to always put: the later indices will simply override the earlier ones
-                    index.put (((CONSTANT_Utf8_info) constant).m_value, i); // note: unadjusted index saved here
-                }
-            }
-            
-            m_CONSTANT_Utf8_index = index;
-        }
-        
-        return m_CONSTANT_Utf8_index;
-    }
-
-
-    private List/* CONSTANT_info */ m_constants; // never null
-    private int m_size;
-    private transient ObjectIntMap /* String(CONSTANT_Utf value) -> int(index) */ m_CONSTANT_Utf8_index;
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/ElementFactory.java b/core/java12/com/vladium/jcd/cls/ElementFactory.java
deleted file mode 100644
index 2922837..0000000
--- a/core/java12/com/vladium/jcd/cls/ElementFactory.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ElementFactory.java,v 1.1.1.1 2004/05/09 16:57:45 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class ElementFactory
-{
-    // public: ................................................................
-    
-    
-    public static IAttributeCollection newAttributeCollection (final int capacity)
-    {
-        return new AttributeCollection (capacity);
-    }
-
-    public static IConstantCollection newConstantCollection (final int capacity)
-    {
-        return new ConstantCollection (capacity);
-    }
-
-    public static IFieldCollection newFieldCollection (final int capacity)
-    {
-        return new FieldCollection (capacity);
-    }
-
-    public static IInterfaceCollection newInterfaceCollection (final int capacity)
-    {
-        return new InterfaceCollection (capacity);
-    }
-
-    public static IMethodCollection newMethodCollection (final int capacity)
-    {
-        return new MethodCollection (capacity);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/FieldCollection.java b/core/java12/com/vladium/jcd/cls/FieldCollection.java
deleted file mode 100644
index f0a061e..0000000
--- a/core/java12/com/vladium/jcd/cls/FieldCollection.java
+++ /dev/null
@@ -1,137 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: FieldCollection.java,v 1.1.1.1 2004/05/09 16:57:45 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
-import com.vladium.jcd.lib.UDataOutputStream;
-import com.vladium.util.IntVector;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-final class FieldCollection implements IFieldCollection
-{
-    // public: ................................................................
-
-    // ACCESSORS:
-        
-    public Field_info get (final int offset)
-    {
-        return (Field_info) m_fields.get (offset);
-    }
-    
-    public int [] get (final ClassDef cls, final String name)
-    {
-        if (cls == null) throw new IllegalArgumentException  ("null input: cls");
-        
-        // TODO: hash impl [not possible without having access to the parent ClassDef]
-        
-        final int count = m_fields.size (); // use size() if class becomes non-final
-        final IntVector result = new IntVector (count);
-
-        for (int f = 0; f < count; ++ f)
-        {
-            final Field_info field = (Field_info) m_fields.get (f);
-            
-            if (field.getName (cls).equals (name))  
-                result.add (f);
-        }
-        
-        return result.values (); // IntVector optimizes for the empty case 
-    }
-    
-    public int size ()
-    {
-        return m_fields.size ();
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final FieldCollection _clone = (FieldCollection) super.clone ();
-            
-            // deep clone:
-            final int fields_count = m_fields.size (); // use size() if class becomes non-final
-            _clone.m_fields = new ArrayList (fields_count);
-            for (int f = 0; f < fields_count; ++ f)
-            {
-                _clone.m_fields.add (((Field_info) m_fields.get (f)).clone ());
-            }
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }        
-    }
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        final int fields_count = m_fields.size (); // use size() if class becomes non-final
-        out.writeU2 (fields_count);
-        
-        for (int i = 0; i < fields_count; i++)
-        {
-            get (i).writeInClassFormat (out);
-        }
-    }
-    
-    // Visitor:
-    
-    public void accept (final IClassDefVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-
-    // MUTATORS:
-
-    public int add (final Field_info field)
-    {
-        final int newoffset = m_fields.size (); // use size() if class becomes non-final
-        m_fields.add (field);
-        
-        return newoffset;
-    }
-    
-    public Field_info set (final int offset, final Field_info field)
-    {
-        return (Field_info) m_fields.set (offset, field);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    FieldCollection (final int capacity)
-    {
-        m_fields = capacity < 0 ? new ArrayList () : new ArrayList (capacity);
-    }
-
-    // private: ...............................................................
-
-    
-    private List/* Field_info */ m_fields; // never null
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/Field_info.java b/core/java12/com/vladium/jcd/cls/Field_info.java
deleted file mode 100644
index 22a9dcd..0000000
--- a/core/java12/com/vladium/jcd/cls/Field_info.java
+++ /dev/null
@@ -1,197 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Field_info.java,v 1.1.1.1 2004/05/09 16:57:45 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import java.io.IOException;
-
-import com.vladium.jcd.cls.attribute.*;
-import com.vladium.jcd.cls.constant.CONSTANT_Utf8_info;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * Each class field is described by a variable-length field_info structure. The
- * format of this structure is
- * <PRE>
- *  field_info {
- *          u2 access_flags;
- *          u2 name_index;
- *          u2 descriptor_index;
- *          u2 attributes_count;
- *          attribute_info attributes[attributes_count];
- *  }
- * </PRE>
- * 
- * The value of the access_flags item is a mask of modifiers used to describe
- * access permission to and properties of a field.<P>
- * 
- * The value of the name_index item must be a valid index into the constant pool
- * table. The constant pool entry at that index must be a {@link CONSTANT_Utf8_info}
- * structure which must represent a valid Java field name stored as a simple (not
- * fully qualified) name, that is, as a Java identifier.<P>
- * 
- * The value of the descriptor_index item must be a valid index into the constant
- * pool table. The constant pool entry at that index must be a
- * {@link CONSTANT_Utf8_info} structure which must represent a valid Java field
- * descriptor.<P>
- * 
- * Each value of the attributes table must be a variable-length attribute structure.
- * A field can have any number of attributes associated with it. The only attribute
- * defined for the attributes table of a field_info structure at the moment
- * is the ConstantValue attribute -- see {@link ConstantValueAttribute_info}.
- *  
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class Field_info implements Cloneable, IAccessFlags
-{
-    // public: ................................................................
-
-    
-    public int m_name_index;
-    public int m_descriptor_index;
-    
-    
-    public Field_info (final int access_flags,
-                       final int name_index, final int descriptor_index,
-                       final IAttributeCollection attributes)
-    {
-        m_access_flags = access_flags;
-        
-        m_name_index = name_index;
-        m_descriptor_index = descriptor_index;
-        
-        m_attributes = attributes;
-    }
-
-    public Field_info (final IConstantCollection constants,
-                       final UDataInputStream bytes)
-        throws IOException
-    {
-        m_access_flags = bytes.readU2 ();
-        
-        m_name_index = bytes.readU2 ();
-        m_descriptor_index = bytes.readU2 ();
-        
-        // TODO: put this logic into AttributeCollection
-        final int attributes_count = bytes.readU2 ();
-        m_attributes = ElementFactory.newAttributeCollection (attributes_count);
-        
-        for (int i = 0; i < attributes_count; i++)
-        {
-            final Attribute_info attribute_info = Attribute_info.new_Attribute_info (constants, bytes);
-            if (DEBUG) System.out.println ("\t[" + i + "] attribute: " + attribute_info);
-            
-            m_attributes.add (attribute_info);
-        }
-    }
-    
-    /**
-     * Returns the field name within the context of 'cls' class definition.
-     * 
-     * @param cls class that contains this field
-     * @return field name
-     */
-    public String getName (final ClassDef cls)
-    {
-        return ((CONSTANT_Utf8_info) cls.getConstants ().get (m_name_index)).m_value;
-    }
-    
-    /**
-     * Returns the descriptor string for this field within the context of 'cls'
-     * class definition.
-     * 
-     * @param cls class that contains this field
-     * @return field typename descriptor
-     */
-    public String getDescriptor (final ClassDef cls)
-    {
-        return ((CONSTANT_Utf8_info) cls.getConstants ().get (m_descriptor_index)).m_value;
-    }
-    
-    public boolean isSynthetic ()
-    {
-        return m_attributes.hasSynthetic ();
-    }
-    
-    // IAccessFlags:
-        
-    public final void setAccessFlags (final int flags)
-    {
-        m_access_flags = flags;
-    }
-
-    public final int getAccessFlags ()
-    {
-        return m_access_flags;
-    }
-    
-    public IAttributeCollection getAttributes ()
-    {
-        return m_attributes;
-    }
-    
-    
-    public String toString ()
-    {
-        return "field_info: [modifiers: 0x" + Integer.toHexString(m_access_flags) + ", name_index = " + m_name_index + ", descriptor_index = " + m_descriptor_index + ']';
-    }
-    
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final Field_info _clone = (Field_info) super.clone ();
-            
-            // do deep copy:
-            _clone.m_attributes = (IAttributeCollection) m_attributes.clone ();
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }
-    }
-    
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {    
-        out.writeU2 (m_access_flags);
-        
-        out.writeU2 (m_name_index);
-        out.writeU2 (m_descriptor_index);
-        
-        m_attributes.writeInClassFormat (out);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-    
-    private int m_access_flags;
-    private IAttributeCollection m_attributes; // never null
-
-    
-    private static final boolean DEBUG = false;
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/IAccessFlags.java b/core/java12/com/vladium/jcd/cls/IAccessFlags.java
deleted file mode 100644
index d6e73c0..0000000
--- a/core/java12/com/vladium/jcd/cls/IAccessFlags.java
+++ /dev/null
@@ -1,68 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IAccessFlags.java,v 1.1.1.1 2004/05/09 16:57:46 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IAccessFlags
-{
-    // public: ................................................................
-
-    static final int ACC_PUBLIC         = 0x0001;
-    static final int ACC_PRIVATE        = 0x0002;
-    static final int ACC_PROTECTED      = 0x0004;
-    static final int ACC_STATIC         = 0x0008;
-    static final int ACC_FINAL          = 0x0010;
-    static final int ACC_SYNCHRONIZED   = 0x0020;
-    static final int ACC_SUPER          = 0x0020; // same bit value as ACC_SYNCHRONIZED
-    static final int ACC_VOLATILE       = 0x0040;
-    static final int ACC_BRIDGE         = 0x0040; // same bit value as ACC_VOLATILE
-    static final int ACC_TRANSIENT      = 0x0080;
-    static final int ACC_NATIVE         = 0x0100;
-    static final int ACC_INTERFACE      = 0x0200;
-    static final int ACC_ABSTRACT       = 0x0400;
-    
-    static final int ALL_ACC [] = new int []
-    {
-        ACC_PUBLIC,
-        ACC_PRIVATE,
-        ACC_PROTECTED,
-        ACC_STATIC,
-        ACC_FINAL,
-        ACC_SYNCHRONIZED,     
-        ACC_VOLATILE,
-        ACC_TRANSIENT,
-        ACC_NATIVE,
-        ACC_INTERFACE,
-        ACC_ABSTRACT,
-    };
-    
-    static final String ALL_ACC_NAMES [] = new String []
-    {
-        "public",
-        "private",
-        "protected",
-        "static",
-        "final",
-        "synchronized",     
-        "volatile",
-        "transient",
-        "native",
-        "interface",
-        "abstract",
-    };
-    
-    void setAccessFlags (int flags);
-    int getAccessFlags ();
-    
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/IAttributeCollection.java b/core/java12/com/vladium/jcd/cls/IAttributeCollection.java
deleted file mode 100644
index 4d79328..0000000
--- a/core/java12/com/vladium/jcd/cls/IAttributeCollection.java
+++ /dev/null
@@ -1,98 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IAttributeCollection.java,v 1.1.1.1 2004/05/09 16:57:46 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import com.vladium.jcd.cls.attribute.*;
-import com.vladium.jcd.compiler.IClassFormatOutput;
-
-// ----------------------------------------------------------------------------
-/**
- * An abstraction of the 'attributes' component of .class format. The contents
- * are {@link Attribute_info} structures. The order in which they appear is
- * unspecified.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IAttributeCollection extends Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-
-    // ACCESSORS:
-    
-    /**
-     * Returns the attribute descriptor at a given offset.
-     * 
-     * @param offset attribute offset [must be in [0, size()) range; input not checked]
-     * @return Attribute_info descriptor [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    Attribute_info get (int offset);
-    
-    boolean hasSynthetic ();
-    boolean hasBridge ();
-    InnerClassesAttribute_info getInnerClassesAttribute ();
-    
-    /**
-     * Returns the number of attributes in this collection [can be 0].
-     */
-    int size ();
-    
-    /**
-     * Returns the total length of this collection when converted to
-     * .class format [including 2 count bytes]
-     */
-    long length ();
-    
-    // Cloneable: adjust the access level of Object.clone():
-    Object clone ();
-    
-    // Visitor:
-    void accept (IClassDefVisitor visitor, Object ctx);
-    
-    
-    // MUTATORS:
-    
-    /**
-     * Adds a new Attribute_info descriptor to this collection. No duplicate
-     * checks are made. It is the responsibility of the caller to ensure
-     * that all data referenced in 'attribute' will eventually appear in the
-     * constant pool.
-     * 
-     * @param attribute new attribute descriptor [may not be null]
-     */
-    int add (Attribute_info attribute);
-    
-    /**
-     * Replaces the Attribute_info descriptor at a given offset. No duplicate
-     * checks are made. It is the responsibility of the caller to ensure that
-     * all data referenced in 'attribute' will eventually appear in the constant
-     * pool.
-     * 
-     * @param offset attribute offset [must be in [0, size()) range; input not checked]
-     * @param attribute new attribute descriptor [may not be null]
-     * @return previous attribute descriptor at this offset [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    Attribute_info set (int offset, Attribute_info attribute);
-    
-    /**
-     * Removes the Attribute_info descriptor at a given offset.
-     * 
-     * @param offset attribute offset [must be in [0, size()) range; input not checked]
-     * @return current attribute descriptor at this offset [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    Attribute_info remove (int offset);
-    
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/IClassDefConstants.java b/core/java12/com/vladium/jcd/cls/IClassDefConstants.java
deleted file mode 100644
index 0b81a94..0000000
--- a/core/java12/com/vladium/jcd/cls/IClassDefConstants.java
+++ /dev/null
@@ -1,25 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IClassDefConstants.java,v 1.1.1.1 2004/05/09 16:57:46 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IClassDefConstants
-{
-    // public: ................................................................
-    
-    String INIT_NAME = "<init>";
-    String CLINIT_NAME = "<clinit>";
-    String CLINIT_DESCRIPTOR = "()V";
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/jcd/cls/IClassDefVisitor.java b/core/java12/com/vladium/jcd/cls/IClassDefVisitor.java
deleted file mode 100644
index e49a6d4..0000000
--- a/core/java12/com/vladium/jcd/cls/IClassDefVisitor.java
+++ /dev/null
@@ -1,28 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IClassDefVisitor.java,v 1.1.1.1 2004/05/09 16:57:46 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-public interface IClassDefVisitor
-{
-    // public: ................................................................
-    
-    Object visit (ClassDef cls, Object ctx);
-    
-    Object visit (IConstantCollection constants, Object ctx);
-    Object visit (IInterfaceCollection interfaces, Object ctx);
-    Object visit (IFieldCollection fields, Object ctx);
-    Object visit (IMethodCollection methods, Object ctx);
-    Object visit (IAttributeCollection attributes, Object ctx);
-
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/IConstantCollection.java b/core/java12/com/vladium/jcd/cls/IConstantCollection.java
deleted file mode 100644
index 3a7931a..0000000
--- a/core/java12/com/vladium/jcd/cls/IConstantCollection.java
+++ /dev/null
@@ -1,175 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IConstantCollection.java,v 1.1.1.1 2004/05/09 16:57:46 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import com.vladium.jcd.cls.constant.*;
-import com.vladium.jcd.compiler.IClassFormatOutput;
-
-// ----------------------------------------------------------------------------
-/**
- * An abstraction of constant pool in .class format. This interface disallows
- * any pool mutation that invalidates already existing pool indices. 
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IConstantCollection extends Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-
-    /**
-     * A custom fail-fast iterator class returned by {@link IConstantCollection#iterator()}.
-     * It allows iterating over all entries in a way that steps over all
-     * 'invalid' inner slots (extra slots consumed by CONSTANT_Long and
-     * CONSTANT_Double entries).
-     */
-    interface IConstantIterator
-    {
-        /**
-         * Returns the next entry slot index.
-         * 
-         * @return int next valid slot index [always positive for a valid slot;
-         * -1 when the enumeration is exhausted]
-         */
-        public int nextIndex ();
-        
-        /**
-         * Returns the next entry. This is a convenience method for doing
-         * get(nextIndex()) and avoiding index bound violation exceptions.
-         * 
-         * @return CONSTANT_info next valid entry [null when the enumeration is
-         * exhausted]
-         */
-        public CONSTANT_info nextConstant ();
-        
-        /**
-         * A convenience method that is equivalent to {@link IConstantCollection#set}
-         * and replaces the entry that was visited last without invalidating
-         * the iterator. 
-         */
-        CONSTANT_info set (CONSTANT_info constant);
-        
-    } // end of nested interface
-    
-    
-    /**
-     * A simple interface to express custom semantics of constant equality.
-     * 
-     * @see IConstantCollection#find(int, IConstantComparator)
-     */
-    interface IConstantComparator
-    {
-        boolean equals (CONSTANT_info constant);
-        
-    } // end of nested interface
-    
-    
-    // ACCESSORS:
-    
-    /**
-     * Returns a CONSTANT_info at a given pool index. Note that 'index' is
-     * 1-based [the way an index would be embedded in bytecode instructions].
-     * Note that because CONSTANT_Long and CONSTANT_Double entries occupy
-     * two consequitive index slots certain index values inside the valid range
-     * can be invalid; use {@link #iterator()} to iterate only over valid entries
-     * in a transparent fashion. 
-     * 
-     * @param index constant pool index [must be in [1, size()] range]
-     * @return CONSTANT_info constant pool entry at this index [never null]
-     * 
-     * @throws IllegalStateException if an attempt is made to reference
-     * an invalid slot index
-     * @throws IndexOutOfBoundsException if an attempt is made to reference
-     * a slot outside of the valid range 
-     */
-    CONSTANT_info get (int index);
-    
-    /**
-     * Returns a fail-fast iterator over all valid entries in the pool. The
-     * resulting object would be invalidated by simultaneous mutation to the
-     * underlying collection pool.
-     * 
-     * @return IConstantIterator iterator over all entries in the collection [never null]
-     */
-    IConstantIterator iterator ();
-    
-    /**
-     * Searches the pool for a matching constant of given type with equality
-     * semantics expressed by 'comparator'. This method guarantees that
-     * when comparator.equals(c) is called c.type() is 'type'. The cost is
-     * O(pool size). When multiple matches exist, the location of the first one
-     * found will be returned (chosen in some indeterministic way).
-     *  
-     * @param type type of constants to filter by [not validated]
-     * @param comparator [may not be null]
-     * @return index of the first found entry [-1 if not found] 
-     * 
-     * @throws IllegalArgumentException if 'comparator' is null
-     */
-    int find (int type, IConstantComparator comparator);
-    
-    /**
-     * Convenience method that can lookup CONSTANT_Utf8 entries in O(1) time
-     * on average. Note that .class format does not guarantee that all such
-     * entries are not duplicated in the pool. When multiple matches exist, the
-     * location of the first one found will be returned (chosen in some
-     * indeterministic way).
-     * 
-     * @param value string value on which to match [may not be null]
-     * @return index of the first found entry [-1 if not found]
-     * 
-     * @throws IllegalArgumentException if 'value' is null
-     */
-    int findCONSTANT_Utf8 (String value);
-    
-    /**
-     * Returns the number of CONSTANT_info entries in this collection. 
-     * 
-     * @return the number of constants in this pool [can be 0]
-     */
-    int size ();
-        
-    // Cloneable: adjust the access level of Object.clone():
-    Object clone ();
-    
-    // Visitor:
-    void accept (IClassDefVisitor visitor, Object ctx);
-    
-
-    // MUTATORS:
-    
-    /**
-     * Appends 'constant' to the end of the collection. No duplicate checks
-     * are made.
-     * 
-     * @param constant new constant [may not be null; input unchecked]
-     * @return the pool index of the newly added entry [always positive]
-     */
-    int add (CONSTANT_info constant);
-    
-    /**
-     * Replaces an existing constant pool entry. A replacement can be made only
-     * for a constant of the same width as the constant currently occupying the
-     * slot. 
-     * 
-     * @param index constant pool index [must be in [1, size()] range]
-     * @param constant new entry to set [may not be null; input unchecked]
-     * @return CONSTANT_info previous contents at this pool index [never null]
-     * 
-     * @throws IllegalArgumentException if the new constant's width is different
-     * from the current entry's
-     * @throws IllegalStateException if an attempt is made to reference
-     * an invalid slot index [see {@link #get(int)}]
-     * @throws IndexOutOfBoundsException if an attempt is made to reference
-     * a slot outside of the valid range
-     */
-    CONSTANT_info set (int index, CONSTANT_info constant);
-    
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/IFieldCollection.java b/core/java12/com/vladium/jcd/cls/IFieldCollection.java
deleted file mode 100644
index 7cab5ee..0000000
--- a/core/java12/com/vladium/jcd/cls/IFieldCollection.java
+++ /dev/null
@@ -1,94 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IFieldCollection.java,v 1.1.1.1 2004/05/09 16:57:46 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import com.vladium.jcd.compiler.IClassFormatOutput;
-
-// ----------------------------------------------------------------------------
-/**
- * An abstraction of the 'fields' component of .class format. The contents
- * are {@link Field_info} structures corresponding to all fields directly
- * declared by this class/interface. The order in which they appear is
- * unspecified.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IFieldCollection extends Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-    
-    // ACCESSORS:
-    
-    /**
-     * Returns {@link Field_info} descriptor at a given offset.
-     * 
-     * @param offset field offset [must be in [0, size()) range; input not checked]
-     * @return Field_info descriptor [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    Field_info get (int offset);
-    
-    /**
-     * Returns an array of offsets for fields named 'name' (empty array if no
-     * matching fields found). Note: even though Java syntax disallows for a class
-     * to have multiple fields with the same name it is possible at the bytecode
-     * level (as long as the type descriptors disambiguate).
-     * 
-     * @param cls class definition providing the constant pool against which to
-     * resolve names [may not be null]
-     * @param name field name [null or empty will result in no matches]
-     * @return array of field offsets in no particular order [never null; could be empty]
-     * 
-     * @throws IllegalArgumentException if 'cls' is null
-     */
-    int [] get (ClassDef cls, String name);
-    
-    /**
-     * Returns the number of fields in this collection [can be 0].
-     */
-    int size ();
-
-    // Cloneable: adjust the access level of Object.clone():
-    Object clone ();
-    
-    // Visitor:
-    void accept (IClassDefVisitor visitor, Object ctx);
-
-
-    // MUTATORS:
-    
-    /**
-     * Adds a new Field_info descriptor to this collection. No duplicate
-     * checks are made. It is the responsibility of the caller to ensure
-     * that all data referenced in 'field' will eventually appear in the
-     * constant pool.
-     * 
-     * @param field new field descriptor [may not be null]
-     * @return new field's offset
-     */
-    int add (Field_info field);
-    
-    /**
-     * Replaces the Field_info descriptor at a given offset. No duplicate
-     * checks are made. No field type compatibility checks are made.  It is
-     * the responsibility of the caller to ensure that all data referenced
-     * in 'field' will eventually appear in the constant pool.
-     * 
-     * @param offset field offset [must be in [0, size()) range; input not checked]
-     * @param field new field descriptor [may not be null]
-     * @return previous field descriptor at this offset [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    Field_info set (int offset, Field_info field);
-        
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/IInterfaceCollection.java b/core/java12/com/vladium/jcd/cls/IInterfaceCollection.java
deleted file mode 100644
index 732b6c0..0000000
--- a/core/java12/com/vladium/jcd/cls/IInterfaceCollection.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IInterfaceCollection.java,v 1.1.1.1 2004/05/09 16:57:46 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import com.vladium.jcd.compiler.IClassFormatOutput;
-
-// ----------------------------------------------------------------------------
-/**
- * An abstraction of the 'interfaces' component of .class format. The contents
- * are constant pool indices of {@link com.vladium.jcd.cls.constant.CONSTANT_Class_info}
- * structures corresponding to direct superinterfaces of this class/interface.
- * The order in which they appear is the left-to-right order of their declaration in
- * the implements/extends clause.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IInterfaceCollection extends Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-
-    // ACCESSORS:
-    
-    /**
-     * Returns the {@link com.vladium.jcd.cls.constant.CONSTANT_Class_info}
-     * constant pool index for offset'th direct superinterface.
-     * 
-     * @param offset superinterface number [must be in [0, size()) range]
-     * @return constant pool index [always positive]  
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    int get (int offset);
-    
-    /**
-     * Returns the number of direct superinterfaces for this class/interface.
-     * 
-     * @return int number of direct superinterfaces [can be 0]
-     */
-    int size ();
-    
-    // Cloneable: adjust the access level of Object.clone():
-    Object clone ();
-    
-    // Visitor:
-    void accept (IClassDefVisitor visitor, Object ctx);
-
-
-    // MUTATORS:
-    
-    /**
-     * Appends a new superinterface pointer to the collection. No duplicate checks are made.
-     * 
-     * @param interface_index constant pool index [must be positive; input not validated]
-     * @return offset of the new pointer [same as {@link #size()}-1 when called
-     * after this method] 
-     */
-    int add (int interface_index);
-    
-    /**
-     * Replaces superinterface pointer number 'offset' with new value 'interface_index'.
-     * No duplicate checks are made. It is the responsibility of the caller to
-     * ensure that the relevant CONSTANT_Class_info descriptor will be found
-     * in the constant pool, in the slot pointed to by 'interface_index'.
-     * 
-     * @param offset offset of the superinterface pointer to replace [must be in [0, size()) range]
-     * @param interface_index constant pool index [must be positive; input not validated]
-     * @return previous value at the given index [always positive]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    int set (int offset, int interface_index);
-    
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/IMethodCollection.java b/core/java12/com/vladium/jcd/cls/IMethodCollection.java
deleted file mode 100644
index 91ad3b8..0000000
--- a/core/java12/com/vladium/jcd/cls/IMethodCollection.java
+++ /dev/null
@@ -1,104 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IMethodCollection.java,v 1.1.1.1 2004/05/09 16:57:46 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import com.vladium.jcd.compiler.IClassFormatOutput;
-
-// ----------------------------------------------------------------------------
-/**
- * An abstraction of the 'methods' component of .class format. The contents
- * are {@link Method_info} structures corresponding to all methods directly
- * declared by this class/interface. The order in which they appear is
- * unspecified.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IMethodCollection extends Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-
-    // ACCESSORS:
-    
-    /**
-     * Returns {@link Method_info} descriptor at a given offset.
-     * 
-     * @param offset method offset [must be in [0, size()) range; input not checked]
-     * @return Method_info descriptor [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    Method_info get (int offset);
-    
-    /**
-     * Returns an array of offsets for methods named 'name' (empty array if no
-     * matching fields found).
-     * 
-     * @param cls class definition providing the constant pool against which to
-     * resolve names [may not be null]
-     * @param name method name [null or empty will result in no matches]
-     * @return array of method offsets in no particular order [never null; could be empty]
-     * 
-     * @throws IllegalArgumentException if 'cls' is null
-     */
-    int [] get (ClassDef cls, String name);
-    
-    /**
-     * Returns the number of methods in this collection [can be 0].
-     */
-    int size ();
-
-    // Cloneable: adjust the access level of Object.clone():
-    Object clone ();
-    
-    // Visitor:
-    void accept (IClassDefVisitor visitor, Object ctx);
-
-    
-    // MUTATORS:
-    
-    /**
-     * Adds a new Method_info descriptor to this collection. No duplicate
-     * checks are made. It is the responsibility of the caller to ensure
-     * that all data referenced in 'method' will eventually appear in the
-     * constant pool.
-     * 
-     * @param method new method descriptor [may not be null]
-     */
-    int add (Method_info method);
-    
-    /**
-     * Replaces the Method_info descriptor at a given offset. No duplicate
-     * checks are made. No method type compatibility checks are made.  It is
-     * the responsibility of the caller to ensure that all data referenced
-     * in 'method' will eventually appear in the constant pool.
-     * 
-     * @param offset method offset [must be in [0, size()) range; input not checked]
-     * @param method new method descriptor [may not be null]
-     * @return previous method descriptor at this offset [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    Method_info set (int offset, Method_info method);
-    
-    // TODO: support this via iterators instead
-    /**
-     * Removes the Method_info descriptor at a given offset. It is
-     * the responsibility of the caller to ensure that the class definition
-     * remains consistent after this change.
-     * 
-     * @param offset method offset [must be in [0, size()) range; input not checked]
-     * @return method descriptor at this offset [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    Method_info remove (int offset);
-    
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/InterfaceCollection.java b/core/java12/com/vladium/jcd/cls/InterfaceCollection.java
deleted file mode 100644
index 9264f07..0000000
--- a/core/java12/com/vladium/jcd/cls/InterfaceCollection.java
+++ /dev/null
@@ -1,110 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: InterfaceCollection.java,v 1.1.1.1 2004/05/09 16:57:46 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataOutputStream;
-import com.vladium.util.IntVector;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-final class InterfaceCollection implements IInterfaceCollection
-{
-    // public: ................................................................
-    
-    // ACCESSORS:
-
-    public int get (final int offset)
-    {
-        return m_interfaces.get (offset);
-    }
-    
-    public int size ()
-    {
-        return m_interfaces.size ();
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final InterfaceCollection _clone = (InterfaceCollection) super.clone ();
-            
-            // deep clone:
-            _clone.m_interfaces = (IntVector) m_interfaces.clone ();
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }        
-    }
-        
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        int _interfaces_count = m_interfaces.size (); // use size() if class becomes non-final
-        out.writeU2 (_interfaces_count);
-        
-        for (int i = 0; i < _interfaces_count; i++)
-        {
-            out.writeU2 (get (i));
-        }
-    }
-    
-    // Visitor:
-    
-    public void accept (final IClassDefVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    
-    // MUTATORS:
-
-    public int add (final int interface_index)
-    {
-        final int newoffset = m_interfaces.size (); // use size() if class becomes non-final
-        m_interfaces.add (interface_index);
-        
-        return newoffset;
-    }
-    
-    public int set (final int offset, final int interface_index)
-    {
-        return m_interfaces.set (offset, interface_index);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    InterfaceCollection (final int capacity)
-    {
-        m_interfaces = capacity < 0 ? new IntVector () : new IntVector (capacity);
-    }
-
-    // private: ...............................................................
-
-    
-    private IntVector m_interfaces; // vector of constant pool indices
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/MethodCollection.java b/core/java12/com/vladium/jcd/cls/MethodCollection.java
deleted file mode 100644
index f0d7340..0000000
--- a/core/java12/com/vladium/jcd/cls/MethodCollection.java
+++ /dev/null
@@ -1,143 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: MethodCollection.java,v 1.1.1.1 2004/05/09 16:57:47 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
-import com.vladium.jcd.lib.UDataOutputStream;
-import com.vladium.util.IntVector;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-final class MethodCollection implements IMethodCollection
-{
-    // public: ................................................................
-
-    // ACCESSORS:
-        
-    public Method_info get (final int offset)
-    {
-        return (Method_info) m_methods.get (offset);
-    }
-    
-    public int [] get (final ClassDef cls, final String name)
-    {
-        if (cls == null) throw new IllegalArgumentException  ("null input: cls");
-        
-        // TODO: hash impl [not possible without having access to the parent ClassDef]
-        
-        final int count = m_methods.size (); // use size() if class becomes non-final
-        final IntVector result = new IntVector (count);
-
-        for (int m = 0; m < count; ++ m)
-        {
-            final Method_info method = (Method_info) m_methods.get (m);
-            
-            if (method.getName (cls).equals (name))  
-                result.add (m);
-        }
-        
-        return result.values (); // IntVector optimizes for the empty case 
-    }
-    
-    public int size ()
-    {
-        return m_methods.size ();
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final MethodCollection _clone = (MethodCollection) super.clone ();
-            
-            // deep clone:
-            final int methods_count = m_methods.size (); // use size() if class becomes non-final
-            _clone.m_methods = new ArrayList (methods_count);
-            for (int m = 0; m < methods_count; ++ m)
-            {
-                _clone.m_methods.add (((Method_info) m_methods.get (m)).clone ());
-            }
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }        
-    }
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        final int methods_count = m_methods.size (); // use size() if class becomes non-final
-        out.writeU2 (methods_count);
-        
-        for (int i = 0; i < methods_count; i++)
-        {
-            get (i).writeInClassFormat (out);
-        }
-    }
-    
-    // Visitor:
-    
-    public void accept (final IClassDefVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-
-    // MUTATORS:
-
-    public int add (final Method_info method)
-    {
-        final int newoffset = m_methods.size ();  // use size() if class becomes non-final
-        m_methods.add (method);
-        
-        return newoffset;
-    }
-    
-    public Method_info set (final int offset, final Method_info method)
-    {
-        return (Method_info) m_methods.set (offset, method);
-    }
-    
-    public Method_info remove (final int offset)
-    {
-        return (Method_info) m_methods.remove (offset);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    MethodCollection (final int capacity)
-    {
-        m_methods = capacity < 0 ? new ArrayList () : new ArrayList (capacity);
-    }
-
-    // private: ...............................................................
-
-    
-    private List/* Method_info */ m_methods; // method collection
-
-} // end of class
-// ----------------------------------------------------------------------------
-
diff --git a/core/java12/com/vladium/jcd/cls/Method_info.java b/core/java12/com/vladium/jcd/cls/Method_info.java
deleted file mode 100644
index f611d2b..0000000
--- a/core/java12/com/vladium/jcd/cls/Method_info.java
+++ /dev/null
@@ -1,220 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Method_info.java,v 1.1.1.1 2004/05/09 16:57:47 vlad_r Exp $
- */
-package com.vladium.jcd.cls;
-
-import java.io.IOException;
-
-import com.vladium.jcd.cls.attribute.*;
-import com.vladium.jcd.cls.constant.CONSTANT_Utf8_info;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * Each class method, and each instance initialization method <init>, is described
- * by a variable-length method_info structure. The structure has the following
- * format:
- * <PRE>
- *  method_info {
- *          u2 access_flags;
- *          u2 name_index;
- *          u2 descriptor_index;
- *          u2 attributes_count;
- *          attribute_info attributes[attributes_count];
- *  }
- * </PRE>
- * 
- * The value of the access_flags item is a mask of modifiers used to describe
- * access permission to and properties of a method or instance initialization method.<P>
- * 
- * The value of the name_index item must be a valid index into the constant pool
- * table. The constant pool entry at that index must be a {@link CONSTANT_Utf8_info}
- * structure representing either one of the special internal method names, either
- * &lt;init&gt; or &lt;clinit&gt;, or a valid Java method name, stored as a simple
- * (not fully qualified) name.<P>
- * 
- * The value of the descriptor_index item must be a valid index into the constant pool
- * table. The constant pool entry at that index must be a {@link CONSTANT_Utf8_info}
- * structure representing a valid Java method descriptor.<P>
- * 
- * Each value of the attributes table must be a variable-length attribute structure.
- * A method can have any number of optional attributes associated with it. The only
- * attributes defined by this specification for the attributes table of a method_info
- * structure are the Code and Exceptions attributes. See {@link CodeAttribute_info}
- * and {@link ExceptionsAttribute_info}.
- *  
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class Method_info implements Cloneable, IAccessFlags
-{
-    // public: ................................................................
-
-    
-    public int m_name_index;
-    public int m_descriptor_index;
-    
-    
-    public Method_info (int access_flags, int name_index, int descriptor_index, IAttributeCollection attributes)
-    {
-        m_access_flags = access_flags;
-        
-        m_name_index = name_index;
-        m_descriptor_index = descriptor_index;
-        
-        m_attributes = attributes;
-    }
-
-
-    public Method_info (final IConstantCollection constants,
-                        final UDataInputStream bytes)
-        throws IOException
-    {
-        m_access_flags = bytes.readU2 ();
-        
-        m_name_index = bytes.readU2 ();
-        m_descriptor_index = bytes.readU2 ();
-        
-        // TODO: put this logic into AttributeCollection
-        
-        final int attributes_count = bytes.readU2 ();        
-        m_attributes = ElementFactory.newAttributeCollection (attributes_count);
-        
-        for (int i = 0; i < attributes_count; ++ i)
-        {
-            final Attribute_info attribute_info = Attribute_info.new_Attribute_info (constants, bytes);
-            
-            m_attributes.add (attribute_info);
-        }
-    }
-   
-    /**
-     * Returns the method name within the context of 'cls' class definition.
-     * 
-     * @param cls class that contains this method
-     * @return method name
-     */
-    public String getName (final ClassDef cls)
-    {
-        return ((CONSTANT_Utf8_info) cls.getConstants ().get (m_name_index)).m_value;
-    }
-    
-    /**
-     * Returns the descriptor string for this method within the context of 'cls'
-     * class definition.
-     * 
-     * @param cls class that contains this method
-     * @return field typename descriptor
-     */
-    public String getDescriptor (final ClassDef cls)
-    {
-        return ((CONSTANT_Utf8_info) cls.getConstants ().get (m_descriptor_index)).m_value;
-    }
-    
-    public boolean isNative ()
-    {
-        return (m_access_flags & ACC_NATIVE) != 0;
-    }
-    
-    public boolean isAbstract ()
-    {
-        return (m_access_flags & ACC_ABSTRACT) != 0;
-    }
-    
-    public boolean isSynthetic ()
-    {
-        return m_attributes.hasSynthetic ();
-    }
-    
-    public boolean isBridge ()
-    {
-        return ((m_access_flags & ACC_BRIDGE) != 0) || m_attributes.hasBridge ();
-    }
-    
-    // IAccessFlags:
-        
-    public final void setAccessFlags (final int flags)
-    {
-        m_access_flags = flags;
-    }
-
-    public final int getAccessFlags ()
-    {
-        return m_access_flags;
-    }
-    
-    
-    public IAttributeCollection getAttributes ()
-    {
-        return m_attributes;
-    }
-    
-    
-    public String toString ()
-    {
-        StringBuffer s = new StringBuffer ();
-        
-        s.append ("method_info: [modifiers: 0x" + Integer.toHexString(m_access_flags) + ", name_index = " + m_name_index + ", descriptor_index = " + m_descriptor_index + "]\n");
-        for (int i = 0; i < m_attributes.size (); i++)
-        {
-            Attribute_info attribute_info = m_attributes.get (i);
-            
-            s.append ("\t[" + i + "] attribute: " + attribute_info + "\n");
-        }
-
-        return s.toString ();
-    }
-    
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final Method_info _clone = (Method_info) super.clone ();
-            
-            // do deep copy:
-            _clone.m_attributes = (IAttributeCollection) m_attributes.clone ();
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }
-    }
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        out.writeU2 (m_access_flags);
-        
-        out.writeU2 (m_name_index);
-        out.writeU2 (m_descriptor_index);
-        
-        m_attributes.writeInClassFormat (out);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-    
-    private int m_access_flags;
-    private IAttributeCollection m_attributes;
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/AttributeElementFactory.java b/core/java12/com/vladium/jcd/cls/attribute/AttributeElementFactory.java
deleted file mode 100644
index 28c15a8..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/AttributeElementFactory.java
+++ /dev/null
@@ -1,36 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AttributeElementFactory.java,v 1.1.1.1 2004/05/09 16:57:47 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
- 
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-abstract class AttributeElementFactory
-{
-    // public: ................................................................
-    
-    public static IExceptionHandlerTable newExceptionHandlerTable (final int capacity)
-    {
-        return new ExceptionHandlerTable (capacity);
-    }
-    
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private AttributeElementFactory () {} // prevent subclassing
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/Attribute_info.java b/core/java12/com/vladium/jcd/cls/attribute/Attribute_info.java
deleted file mode 100644
index ff6b25b..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/Attribute_info.java
+++ /dev/null
@@ -1,204 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Attribute_info.java,v 1.1.1.1 2004/05/09 16:57:47 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.cls.ClassDef;
-import com.vladium.jcd.cls.IConstantCollection;
-import com.vladium.jcd.cls.constant.*;
-import com.vladium.jcd.compiler.IClassFormatOutput;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * Abstract base for all XXXAttribute_info structures. It also works in conjunction
- * with {@link GenericAttribute_info} class to process all unrecognized attributes.<P>
- * 
- * Attributes are used in the {@link com.vladium.jcd.cls.ClassDef}, {@link com.vladium.jcd.cls.Field_info},
- * {@link com.vladium.jcd.cls.Method_info}, and {@link CodeAttribute_info}
- * structures of the .class file format. All attributes have the following
- * general format:
- * <PRE>
- *  attribute_info {
- *          u2 attribute_name_index;
- *          u4 attribute_length;
- *          u1 info[attribute_length];
- *  }
- * </PRE>
- * 
- * For all attributes, the attribute_name_index must be a valid unsigned 16-bit
- * index into the constant pool of the class. The constant pool entry at
- * attribute_name_index must be a {@link com.vladium.jcd.cls.constant.CONSTANT_Utf8_info}
- * string representing the name of the attribute. The value of the attribute_length
- * item indicates the length of the subsequent information in bytes. The length
- * does not include the initial six bytes that contain the attribute_name_index
- * and attribute_length items.
- * 
- * @see GenericAttribute_info
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-abstract class Attribute_info implements Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-    
-    public static final String ATTRIBUTE_CODE               = "Code";
-    public static final String ATTRIBUTE_CONSTANT_VALUE     = "ConstantValue";
-    public static final String ATTRIBUTE_LINE_NUMBER_TABLE  = "LineNumberTable";
-    public static final String ATTRIBUTE_EXCEPTIONS         = "Exceptions";
-    public static final String ATTRIBUTE_SYNTHETIC          = "Synthetic";
-    public static final String ATTRIBUTE_BRIDGE             = "Bridge";
-    public static final String ATTRIBUTE_SOURCEFILE         = "SourceFile";
-    public static final String ATTRIBUTE_INNERCLASSES       = "InnerClasses";
-
-    /**
-     * Constant pool index for {@link com.vladium.jcd.cls.constant.CONSTANT_Utf8_info}
-     * string representing the name of this attribute [always positive].
-     */
-    public int m_name_index;
-    
-    /**
-     * Returns the name for this attribute within the constant pool context of 'cls'
-     * class definition.
-     * 
-     * @param cls class that contains this attribute
-     * @return attribute name
-     */
-    public String getName (final ClassDef cls)
-    {
-        return ((CONSTANT_Utf8_info) cls.getConstants ().get (m_name_index)).m_value;
-    }
-    
-    /**
-     * Returns the total length of this attribute when converted to
-     * .class format [including the 6-byte header]
-     */
-    public abstract long length (); // including the 6-byte header
-    
-    // Visitor:
-    
-    public abstract void accept (IAttributeVisitor visitor, Object ctx); 
-    
-    public abstract String toString ();
-    
-    // TODO: use a hashmap lookup in this method + control which set of attrs get mapped to generic
-    /**
-     * Parses out a single Attribute_info element out of .class data in
-     * 'bytes'.
-     * 
-     * @param constants constant pool for the parent class [may not be null; not validated]
-     * @param bytes input .class data stream [may not be null; not validated]
-     *  
-     * @return a single parsed attribute
-     * 
-     * @throws IOException on input errors
-     */
-    public static Attribute_info new_Attribute_info (final IConstantCollection constants,
-                                                     final UDataInputStream bytes)
-        throws IOException
-    {
-        final int attribute_name_index = bytes.readU2 ();
-        final long attribute_length = bytes.readU4 ();
-        
-        final CONSTANT_Utf8_info attribute_name = (CONSTANT_Utf8_info) constants.get (attribute_name_index);
-        final String name = attribute_name.m_value;
-                
-        if (ATTRIBUTE_CODE.equals (name))
-        {
-            return new CodeAttribute_info (constants, attribute_name_index, attribute_length, bytes);
-        }
-        else if (ATTRIBUTE_CONSTANT_VALUE.equals (name))
-        {
-            return new ConstantValueAttribute_info (attribute_name_index, attribute_length, bytes);
-        }
-        else if (ATTRIBUTE_EXCEPTIONS.equals (name))
-        {
-            return new ExceptionsAttribute_info (attribute_name_index, attribute_length, bytes);
-        }
-        else if (ATTRIBUTE_INNERCLASSES.equals (name))
-        {
-            return new InnerClassesAttribute_info (attribute_name_index, attribute_length, bytes);
-        }
-        else if (ATTRIBUTE_SYNTHETIC.equals (name))
-        {
-            return new SyntheticAttribute_info (attribute_name_index, attribute_length);
-        }
-        else if (ATTRIBUTE_BRIDGE.equals (name))
-        {
-            return new BridgeAttribute_info (attribute_name_index, attribute_length);
-        }
-        else if (ATTRIBUTE_LINE_NUMBER_TABLE.equals (name))
-        {
-            return new LineNumberTableAttribute_info (attribute_name_index, attribute_length, bytes);
-        }
-        else if (ATTRIBUTE_SOURCEFILE.equals (name))
-        {
-            return new SourceFileAttribute_info (attribute_name_index, attribute_length, bytes);
-        }
-        else
-        {
-            // default:
-            return new GenericAttribute_info (attribute_name_index, attribute_length, bytes);
-        }
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Chains to super.clone() and removes CloneNotSupportedException
-     * from the method signature.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            return super.clone ();
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }
-    }
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (UDataOutputStream out) throws IOException
-    {   
-        out.writeU2 (m_name_index);
-        out.writeU4 (length () - 6); // don't use m_attribute_length
-    }
-    
-    // protected: .............................................................
-
-    /*
-    protected Attribute_info (UDataInputStream bytes) throws IOException
-    {
-        //m_name_index = bytes.readU2 ();
-        //m_attribute_length = bytes.readU4 ();
-    }
-    */
-        
-    protected Attribute_info (final int attribute_name_index, final long attribute_length)
-    {
-        m_name_index = attribute_name_index;
-        m_attribute_length = attribute_length;
-    }
-    
-    // TODO: remove this field as it is invalidated easily by most attribute mutations
-    protected long m_attribute_length; // excluding the 6-byte header
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/BridgeAttribute_info.java b/core/java12/com/vladium/jcd/cls/attribute/BridgeAttribute_info.java
deleted file mode 100644
index 8a43137..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/BridgeAttribute_info.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: BridgeAttribute_info.java,v 1.1.1.1.2.1 2004/07/10 03:34:52 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * New attribute added by J2SE 1.5
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class BridgeAttribute_info extends Attribute_info
-{
-    // public: ................................................................
-    
-    
-    public BridgeAttribute_info (final int attribute_name_index)
-    {
-        super (attribute_name_index, 0);
-    }
-    
-    
-    public long length ()
-    {
-        return 6;
-    }
-    
-    // Visitor:
-    
-    public void accept (final IAttributeVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        return "BridgeAttribute_info: [attribute_name_index = " + m_name_index + ", attribute_length = " + m_attribute_length + ']';
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {        
-        return super.clone ();    
-    }
-       
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-    }
-    
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-
-    BridgeAttribute_info (final int attribute_name_index, final long attribute_length)
-    {
-        super (attribute_name_index, attribute_length);
-    }
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
-
diff --git a/core/java12/com/vladium/jcd/cls/attribute/CodeAttribute_info.java b/core/java12/com/vladium/jcd/cls/attribute/CodeAttribute_info.java
deleted file mode 100644
index 597530e..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/CodeAttribute_info.java
+++ /dev/null
@@ -1,262 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CodeAttribute_info.java,v 1.1.1.1 2004/05/09 16:57:47 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.cls.ElementFactory;
-import com.vladium.jcd.cls.IAttributeCollection;
-import com.vladium.jcd.cls.IConstantCollection;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The Code attribute is a variable-length attribute used in the attributes
- * table of {@link com.vladium.jcd.cls.Method_info} structures. A Code attribute
- * contains the JVM instructions and auxiliary information for a single Java method,
- * instance initialization method, or class or interface initialization method.
- * Every Java Virtual Machine implementation must recognize Code attributes. There
- * must be exactly one Code attribute in each method_info structure.<P>
- * 
- * The Code attribute has the format
- * <PRE>
- *  Code_attribute {
- *          u2 attribute_name_index;
- *          u4 attribute_length;
- *          u2 max_stack;
- *          u2 max_locals;
- *          u4 code_length;
- *          u1 code[code_length];
- *          u2 exception_table_length;
- *          {            u2 start_pc;
- *                        u2 end_pc;
- *                        u2  handler_pc;
- *                        u2  catch_type;
- *          }        exception_table[exception_table_length];
- *
- *          u2 attributes_count;
- *          attribute_info attributes[attributes_count];
- *  }
- * </PRE>
- *
- * The value of the max_stack item gives the maximum number of words on the operand
- * stack at any point during execution of this method.<P>
- * 
- * The value of the max_locals item gives the number of local variables used by this
- * method, including the parameters passed to the method on invocation. The index of
- * the first local variable is 0 . The greatest local variable index for a one-word
- * value is max_locals-1 . The greatest local variable index for a two-word value is
- * max_locals-2.<P>
- * 
- * The value of the code_length item gives the number of bytes in the code array for
- * this method. The value of code_length must be greater than zero; the code array must
- * not be empty.The code array gives the actual bytes of Java Virtual Machine code that
- * implement the method.<P>
- * 
- * The value of the exception_table_length item gives the number of entries in the
- * exception_table table. Each entry in the exception_table array describes one
- * exception handler in the code array: see {@link Exception_info}.<P>
- * 
- * The value of the attributes_count item indicates the number of attributes of the Code
- * attribute. Each value of the attributes table must be a variable-length attribute
- * structure. A Code attribute can have any number of optional attributes associated
- * with it.
- *  
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CodeAttribute_info extends Attribute_info
-{
-    // public: ................................................................
-
-
-    public static final byte [] EMPTY_BYTE_ARRAY = new byte [0];
-    
-    public int m_max_stack, m_max_locals;
-    
-    
-    
-    public CodeAttribute_info (final int attribute_name_index,
-                               final int max_stack, int max_locals,
-                               final byte [] code, 
-                               final IExceptionHandlerTable exceptionHandlerTable,
-                               final IAttributeCollection attributes)
-    {
-        super (attribute_name_index, 8 + (code != null ? code.length : 0) + exceptionHandlerTable.length () + attributes.length ());
-        
-        m_max_stack = max_stack;
-        m_max_locals = max_locals;
-        
-        m_code = (code != null ? code : EMPTY_BYTE_ARRAY);
-        m_codeSize = m_code.length;
-        
-        m_exceptionHandlerTable = exceptionHandlerTable;
-        m_attributes = attributes;
-    }
-    
-    /**
-     * NOTE: must also use getCodeSize() 
-     * @return
-     */
-    public final byte [] getCode ()
-    {
-        return m_code;
-    }
-    
-    public final int getCodeSize ()
-    {
-        return m_codeSize;
-    }
-    
-    public IAttributeCollection getAttributes ()
-    {
-        return m_attributes;
-    }
-    
-    public IExceptionHandlerTable getExceptionTable ()
-    {
-        return m_exceptionHandlerTable;
-    }
-    
-    public long length ()
-    {
-        return 14 + m_codeSize + m_exceptionHandlerTable.length () + m_attributes.length ();
-    }
-    
-    // Visitor:
-    
-    public void accept (final IAttributeVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    
-    public String toString ()
-    {
-        String eol = System.getProperty ("line.separator");
-        
-        StringBuffer s = new StringBuffer ();
-        
-        s.append ("CodeAttribute_info: [attribute_name_index = " + m_name_index + ", attribute_length = " + m_attribute_length + "]" + eol);
-        s.append ("    max_stack/max_locals = " + m_max_stack + '/' + m_max_locals + eol);
-        s.append ("    code [length " + m_codeSize + "]" + eol);
-        
-        for (int a = 0; a < m_attributes.size (); ++ a)
-        {
-            s.append ("         " + m_attributes.get (a) + eol);
-        }
-       
-        
-        return s.toString ();
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        final CodeAttribute_info _clone = (CodeAttribute_info) super.clone ();
-        
-        // do deep copy:
-        
-        _clone.m_code = (m_codeSize == 0 ? EMPTY_BYTE_ARRAY : (byte []) m_code.clone ()); // does not trim
-        _clone.m_exceptionHandlerTable = (IExceptionHandlerTable) m_exceptionHandlerTable.clone ();
-        _clone.m_attributes = (IAttributeCollection) m_attributes.clone ();
-        
-        return _clone;
-    }
-    
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeU2 (m_max_stack);
-        out.writeU2 (m_max_locals);
-    
-        out.writeU4 (m_codeSize);
-        out.write (m_code, 0, m_codeSize); // TODO: THIS IS WRONG
-        
-        m_exceptionHandlerTable.writeInClassFormat (out);
-        m_attributes.writeInClassFormat (out);
-    }
-    
-    
-    public void setCode (final byte [] code, final int codeSize)
-    {
-        m_code = code;
-        m_codeSize = codeSize;
-    }
-        
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    CodeAttribute_info (final IConstantCollection constants,
-                        final int attribute_name_index, final long attribute_length,
-                        final UDataInputStream bytes)
-        throws IOException
-    {
-        super (attribute_name_index, attribute_length);
-        
-        m_max_stack = bytes.readU2 ();
-        m_max_locals = bytes.readU2 ();
-        
-        final long code_length = bytes.readU4 ();
-        
-        m_code = new byte [(int) code_length];
-        bytes.readFully (m_code);
-        m_codeSize = (int) code_length;
-        
-        
-        final int exception_table_length = bytes.readU2 ();
-        m_exceptionHandlerTable = AttributeElementFactory.newExceptionHandlerTable (exception_table_length);
-        
-        for (int i = 0; i < exception_table_length; ++ i)
-        {
-            Exception_info exception_info = new Exception_info (bytes);
-            if (DEBUG) System.out.println ("\t[" + i + "] exception: " + exception_info);
-            
-            m_exceptionHandlerTable.add (exception_info);
-        }
-        
-        
-        // TODO: put this logic into AttributeCollection
-        final int attributes_count = bytes.readU2 ();
-        m_attributes = ElementFactory.newAttributeCollection (attributes_count);
-        
-        for (int i = 0; i < attributes_count; ++ i)
-        {
-            Attribute_info attribute_info = Attribute_info.new_Attribute_info (constants, bytes);
-            if (DEBUG) System.out.println ("\t[" + i + "] attribute: " + attribute_info);
-            
-            m_attributes.add (attribute_info);
-        }
-    }
-
-    // private: ...............................................................
-
-
-    private byte [] m_code; // never null [valid content extent is m_codeSize]
-    private int m_codeSize;
-    
-    private IExceptionHandlerTable m_exceptionHandlerTable; // never null
-    private IAttributeCollection m_attributes; // never null
-    
-        
-    private static final boolean DEBUG = false;
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/ConstantValueAttribute_info.java b/core/java12/com/vladium/jcd/cls/attribute/ConstantValueAttribute_info.java
deleted file mode 100644
index f6b51d8..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/ConstantValueAttribute_info.java
+++ /dev/null
@@ -1,136 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ConstantValueAttribute_info.java,v 1.1.1.1 2004/05/09 16:57:47 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.cls.ClassDef;
-import com.vladium.jcd.cls.constant.CONSTANT_literal_info;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The ConstantValue attribute is a fixed-length attribute used in the attributes
- * table of the {@link com.vladium.jcd.cls.Field_info} structures. A ConstantValue
- * attribute represents the value of a constant field that must be (explicitly or
- * implicitly) static; that is, the ACC_STATIC bit in the flags item of the
- * Field_info structure must be set. The field is not required to be final. There
- * can be no more than one ConstantValue attribute in the attributes table of a
- * given Field_info structure. The constant field represented by the Field_info
- * structure is assigned the value referenced by its ConstantValue attribute as
- * part of its initialization.<P>
- * 
- * The ConstantValue attribute has the format
- * <PRE>
- *  ConstantValue_attribute {
- *          u2 attribute_name_index;
- *          u4 attribute_length;
- *          u2 constantvalue_index;
- *  }
- * </PRE>
- * 
- * The value of the constantvalue_index item must be a valid index into the constant
- * pool table. The constant pool entry at that index must give the constant value
- * represented by this attribute.<P>
- * 
- * The constant pool entry must be of a type appropriate to the field, as shown below:
- * 
- * <TABLE>
- * <TR><TH>Field Type</TH>                      <TH>Entry Type</TH></TR>
- * <TR><TD>long</TD>                            <TD>CONSTANT_Long</TD></TR>
- * <TR><TD>float</TD>                           <TD>CONSTANT_Float</TD></TR>
- * <TR><TD>double</TD>                          <TD>CONSTANT_Double</TD></TR>
- * <TR><TD>int, short, char, byte, boolean</TD> <TD>CONSTANT_Integer</TD></TR>
- * <TR><TD>java.lang.String</TD>                <TD>CONSTANT_String</TD></TR>
- * </TABLE>
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class ConstantValueAttribute_info extends Attribute_info
-{
-    // public: ................................................................
-
-    
-    public int m_value_index;
-    
-    
-    public ConstantValueAttribute_info (final int attribute_name_index, final int value_index)
-    {
-        super (attribute_name_index, 2);
-        
-        m_value_index = value_index;
-    }
-    
-    public CONSTANT_literal_info getValue (final ClassDef cls)
-    {
-        return (CONSTANT_literal_info) cls.getConstants ().get (m_value_index);
-    }
-    
-    public long length ()
-    {
-        return 8;
-    }
-    
-    // Visitor:
-    
-    public void accept (final IAttributeVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        // TODO: return more data here
-        return "ConstantValueAttribute_info: [attribute_name_index = " + m_name_index + ", attribute_length = " + m_attribute_length + ']';
-    
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {        
-        return super.clone ();    
-    }
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeU2 (m_value_index);
-    }
-    
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-
-    ConstantValueAttribute_info (final int attribute_name_index, final long attribute_length,
-                                 final UDataInputStream bytes)
-        throws IOException
-    {
-        super (attribute_name_index, attribute_length);
-        
-        m_value_index = bytes.readU2 ();
-        if (DEBUG) System.out.println ("\tconstantvalue_index: " + m_value_index);
-    }
-
-    // private: ...............................................................
-
-    
-    private static final boolean DEBUG = false;
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/DeclaredExceptionTable.java b/core/java12/com/vladium/jcd/cls/attribute/DeclaredExceptionTable.java
deleted file mode 100644
index c4ffd8e..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/DeclaredExceptionTable.java
+++ /dev/null
@@ -1,108 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: DeclaredExceptionTable.java,v 1.1.1.1 2004/05/09 16:57:47 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataOutputStream;
-import com.vladium.util.IntVector;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-final class DeclaredExceptionTable implements IDeclaredExceptionTable
-{
-    // public: ................................................................
-
-    // ACCESSORS:
-
-    public int get (final int offset)
-    {
-        return m_exceptions.get (offset);
-    }
-    
-    public int size ()
-    {
-        return m_exceptions.size ();
-    }
-    
-    public long length ()
-    {
-        return (1 + m_exceptions.size ()) << 1; // use size() if class becomes non-final
-    }
-        
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final DeclaredExceptionTable _clone = (DeclaredExceptionTable) super.clone ();
-            
-            // deep clone:
-            _clone.m_exceptions = (IntVector) m_exceptions.clone ();
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }        
-    }
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        int number_of_exceptions = m_exceptions.size (); // use size() if class becomes non-final
-        out.writeU2 (number_of_exceptions);
-        
-        for (int i = 0; i < number_of_exceptions; i++)
-        {
-            out.writeU2 (get (i));
-        }
-    }
-
-
-    // MUTATORS:
-        
-    public int add (final int exception_index)
-    {
-        final int newoffset = m_exceptions.size (); // use size() if class becomes non-final
-        m_exceptions.add (exception_index);
-        
-        return newoffset;
-    }
-    
-    public int set (final int offset, final int exception_index)
-    {
-        return m_exceptions.set (offset, exception_index);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    DeclaredExceptionTable (final int capacity)
-    {
-         m_exceptions = capacity < 0 ? new IntVector () : new IntVector (capacity);
-    }
-
-    // private: ...............................................................
-
-    
-    private IntVector m_exceptions;
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/ExceptionHandlerTable.java b/core/java12/com/vladium/jcd/cls/attribute/ExceptionHandlerTable.java
deleted file mode 100644
index 074117b..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/ExceptionHandlerTable.java
+++ /dev/null
@@ -1,114 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ExceptionHandlerTable.java,v 1.1.1.1 2004/05/09 16:57:47 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-final class ExceptionHandlerTable implements IExceptionHandlerTable
-{
-    // public: ................................................................
-
-    // ACCESSORS:
-    
-    public Exception_info get (final int offset)
-    {
-        return (Exception_info) m_exceptions.get (offset);
-    }
-    
-    public int size ()
-    {
-        return m_exceptions.size ();
-    }
-    
-    public long length ()
-    {
-        return 2 + (m_exceptions.size () << 3); // use size() if class becomes non-final
-    }
-        
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final ExceptionHandlerTable _clone = (ExceptionHandlerTable) super.clone ();
-            
-            // deep clone:
-            final int exceptions_count = m_exceptions.size (); // use size() if class becomes non-final
-            _clone.m_exceptions = new ArrayList (exceptions_count);
-            for (int e = 0; e < exceptions_count; ++ e)
-            {
-                _clone.m_exceptions.add (((Exception_info) m_exceptions.get (e)).clone ());
-            }
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }        
-    }
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        int exception_table_length = m_exceptions.size (); // use size() if class becomes non-final
-        out.writeU2 (exception_table_length);
-        
-        for (int i = 0; i < exception_table_length; i++)
-        {
-            get (i).writeInClassFormat (out);
-        }
-    }
-
-
-    // MUTATORS:
-
-    public int add (final Exception_info exception)
-    {
-        final int newoffset = m_exceptions.size (); // use size() if class becomes non-final
-        m_exceptions.add (exception);
-        
-        return newoffset;
-    }
-    
-    public Exception_info set (final int offset, final Exception_info exception)
-    {
-        return (Exception_info) m_exceptions.set (offset, exception);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    ExceptionHandlerTable (final int capacity)
-    {
-        m_exceptions = capacity < 0 ? new ArrayList () : new ArrayList (capacity);
-    }
-
-    // private: ...............................................................
-
-
-    private List/* Exception_info */ m_exceptions;
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/Exception_info.java b/core/java12/com/vladium/jcd/cls/attribute/Exception_info.java
deleted file mode 100644
index cc9872e..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/Exception_info.java
+++ /dev/null
@@ -1,125 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Exception_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.compiler.IClassFormatOutput;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * An Exception_info is an entry layout format for {@link ExceptionHandlerTable}. Each
- * entry contains the following items: 
- * <PRE>
- *    start_pc, end_pc 
- * </PRE>
- * The values of the two items start_pc and end_pc indicate the ranges in the code
- * array at which the exception handler is active. The value of start_pc must be
- * a valid index into the code array of the opcode of an instruction. The value of
- * end_pc either must be a valid index into the code array of the opcode of an
- * instruction, or must be equal to code_length , the length of the code array.
- * The value of start_pc must be less than the value of end_pc.<P>
- * 
- * The start_pc is inclusive and end_pc is exclusive; that is, the exception handler
- * must be active while the program counter is within the interval [start_pc, end_pc).
- * <PRE>
- *    handler_pc 
- * </PRE>
- * The value of the handler_pc item indicates the start of the exception handler.
- * The value of the item must be a valid index into the code array, must be the index
- * of the opcode of an instruction, and must be less than the value of the code_length
- * item.
- * <PRE>
- *    catch_type
- * </PRE>
- * If the value of the catch_type item is nonzero, it must be a valid index into the
- * constant_pool table. The constant_pool entry at that index must be a
- * {@link com.vladium.jcd.cls.constant.CONSTANT_Class_info} structure representing
- * a class of exceptions that this exception handler is designated to catch.
- * This class must be the class Throwable or one of its subclasses. The exception
- * handler will be called only if the thrown exception is an instance of the given
- * class or one of its subclasses.<P>
- * 
- * If the value of the catch_type item is zero, this exception handler is called for
- * all exceptions. This is used to implement finally. 
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class Exception_info implements Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-
-    
-    public int m_start_pc, m_end_pc, m_handler_pc, m_catch_type;
-    
-    
-    public Exception_info (final int start_pc, final int end_pc,
-                           final int handler_pc, final int catch_type)
-    {
-        m_start_pc = start_pc;
-        m_end_pc = end_pc;
-        m_handler_pc = handler_pc;
-        m_catch_type = catch_type;
-    }
-    
-    
-    public String toString ()
-    {
-        return "exception_info: [start_pc/end_pc = " + m_start_pc + '/' + m_end_pc +
-               ", handler_pc = " + m_handler_pc +
-               ", catch_type = " + m_catch_type + ']';
-    }
-     
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {    
-            return super.clone ();
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }        
-    }
-      
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        out.writeU2 (m_start_pc);
-        out.writeU2 (m_end_pc);
-        out.writeU2 (m_handler_pc);
-        out.writeU2 (m_catch_type);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    Exception_info (final UDataInputStream bytes) throws IOException
-    {
-        m_start_pc = bytes.readU2 ();
-        m_end_pc = bytes.readU2 ();
-        m_handler_pc = bytes.readU2 ();
-        m_catch_type = bytes.readU2 ();
-    }
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/ExceptionsAttribute_info.java b/core/java12/com/vladium/jcd/cls/attribute/ExceptionsAttribute_info.java
deleted file mode 100644
index dd1837a..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/ExceptionsAttribute_info.java
+++ /dev/null
@@ -1,135 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ExceptionsAttribute_info.java,v 1.1.1.1 2004/05/09 16:57:47 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The Exceptions attribute is a variable-length attribute used in the attributes
- * table of a {@link com.vladium.jcd.cls.Method_info} structure. The Exceptions
- * attribute indicates which checked exceptions a method may throw. There must be
- * exactly one Exceptions attribute in each method_info structure.<P>
- * 
- * The Exceptions attribute has the following format:
- * <PRE>
- * Exceptions_attribute {
- *          u2 attribute_name_index;
- *          u4 attribute_length;
- *          u2 number_of_exceptions;
- *          u2 exception_index_table[number_of_exceptions];
- *  }
- * </PRE>
- * The value of the number_of_exceptions item indicates the number of entries
- * in the exception_index_table.<P>
- * 
- * Each nonzero value in the exception_index_table array must be a valid index
- * into the constant_pool table. For each table item, if
- * exception_index_table[i] != 0 , where 0 &lt; i &lt; number_of_exceptions,
- * then the constant_pool entry at index exception_index_table[i] must be a
- * {@link com.vladium.jcd.cls.constant.CONSTANT_Class_info} structure representing
- * a class type that this method is declared to throw -- see {@link DeclaredExceptionTable}.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class ExceptionsAttribute_info extends Attribute_info
-{
-    // public: ................................................................
-
-    // TODO: merge IDeclaredExceptionTable into this class
-    
-    public ExceptionsAttribute_info (final int attribute_name_index,
-                                     final IDeclaredExceptionTable exceptions)
-    {
-        super (attribute_name_index, exceptions.length ());
-    
-        m_exceptions = exceptions;
-    }
-    
-    public IDeclaredExceptionTable getDeclaredExceptions ()
-    {
-        return m_exceptions;
-    }
-    
-    public long length ()
-    {
-        return 6 + m_exceptions.length ();
-    }
-    
-    // Visitor:
-    
-    public void accept (final IAttributeVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        // TODO: return more data here
-        return "ExceptionsAttribute_info: [attribute_name_index = " + m_name_index + ", attribute_length = " + m_attribute_length + ']';
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        final ExceptionsAttribute_info _clone = (ExceptionsAttribute_info) super.clone ();
-        
-        // do deep copy:
-        _clone.m_exceptions = (IDeclaredExceptionTable) m_exceptions.clone ();
-        
-        return _clone;        
-    }
-       
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        m_exceptions.writeInClassFormat (out);
-    }
-    
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-
-    
-    ExceptionsAttribute_info (final int attribute_name_index, final long attribute_length,
-                              final UDataInputStream bytes)
-        throws IOException
-    {
-        super (attribute_name_index, attribute_length);
-        
-        final int number_of_exceptions = bytes.readU2 ();
-        m_exceptions = new DeclaredExceptionTable (number_of_exceptions);
-        
-        for (int i = 0; i < number_of_exceptions; i++)
-        {
-            final int exception_index = bytes.readU2 ();
-            
-            m_exceptions.add (exception_index);
-        }
-    }
-    
-    // private: ...............................................................
-
-
-    private IDeclaredExceptionTable m_exceptions;
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/GenericAttribute_info.java b/core/java12/com/vladium/jcd/cls/attribute/GenericAttribute_info.java
deleted file mode 100644
index 008b0d4..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/GenericAttribute_info.java
+++ /dev/null
@@ -1,104 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: GenericAttribute_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * This attribute structure is used during parsing to absorb all attribute types
- * that are not currently recognized.
- * 
- * @see Attribute_info
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class GenericAttribute_info extends Attribute_info
-{
-    // public: ................................................................
-
-    
-    public byte [] m_info;
-    
-    
-    public GenericAttribute_info (final int attribute_name_index, final byte [] info)
-    {
-        super (attribute_name_index, (info != null ? info.length : 0));
-        
-        m_info = (info != null ? info : EMPTY_BYTE_ARRAY);
-    }
-    
-    
-    public long length ()
-    {
-        return 6 + m_info.length; 
-    }
-    
-    // Visitor:
-    
-    public void accept (final IAttributeVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        return "generic attribute_info: [attribute_name_index = " + m_name_index + ", attribute_length = " + m_attribute_length + ']';
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        final GenericAttribute_info _clone = (GenericAttribute_info) super.clone ();
-        
-        // do deep copy:
-        _clone.m_info = (m_info.length == 0 ? EMPTY_BYTE_ARRAY : (byte []) m_info.clone ());
-        
-        return _clone;
-    }
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.write (m_info, 0, m_info.length);
-    }
-    
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-
-    GenericAttribute_info (final int attribute_name_index, final long attribute_length,
-                           final UDataInputStream bytes)
-        throws IOException
-    {
-        super (attribute_name_index, attribute_length);
-        
-        m_info = new byte [(int) m_attribute_length];
-        bytes.readFully (m_info);
-    }
-
-    // private: ...............................................................
-
-    
-    private static final byte [] EMPTY_BYTE_ARRAY = new byte [0];
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/IAttributeVisitor.java b/core/java12/com/vladium/jcd/cls/attribute/IAttributeVisitor.java
deleted file mode 100644
index e935968..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/IAttributeVisitor.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IAttributeVisitor.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IAttributeVisitor
-{
-    // public: ................................................................
-    
-    Object visit (GenericAttribute_info attribute, Object ctx);
-    
-    Object visit (CodeAttribute_info attribute, Object ctx);
-    Object visit (ConstantValueAttribute_info attribute, Object ctx);
-    Object visit (ExceptionsAttribute_info attribute, Object ctx);
-    Object visit (LineNumberTableAttribute_info attribute, Object ctx);
-    Object visit (SourceFileAttribute_info attribute, Object ctx);
-    Object visit (SyntheticAttribute_info attribute, Object ctx);
-    Object visit (BridgeAttribute_info attribute, Object ctx);
-    Object visit (InnerClassesAttribute_info attribute, Object ctx);
-
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/IDeclaredExceptionTable.java b/core/java12/com/vladium/jcd/cls/attribute/IDeclaredExceptionTable.java
deleted file mode 100644
index 2a4ff15..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/IDeclaredExceptionTable.java
+++ /dev/null
@@ -1,84 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IDeclaredExceptionTable.java,v 1.1.1.1.2.1 2004/07/10 03:34:52 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import com.vladium.jcd.compiler.IClassFormatOutput;
-
-// ----------------------------------------------------------------------------
-/**
- * This table is a structure nested within {@link ExceptionsAttribute_info}
- * structure. It is a table of unsigned 16-bit indexes into constant pool. Each
- * index points to a {@link com.vladium.jcd.cls.constant.CONSTANT_Class_info}
- * entry representing an exception a method can throw [in unspecified order].
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IDeclaredExceptionTable extends Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-
-    // ACCESSORS:
-    
-    /**
-     * Returns the {@link com.vladium.jcd.cls.constant.CONSTANT_Class_info} constant
-     * pool index for offset'th exception type thrown by the method that contains
-     * this this exception index table in its ExceptionsAttribute_info attribute.
-     * 
-     * @param offset thrown exception class number [must be in [0, size()) range]
-     * @return constant pool index [always positive]  
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    int get (int offset);
-    
-    /**
-     * Returns the number of exception types the containing method professes
-     * to throw.
-     */
-    int size ();
-    
-    /**
-     * Returns the total length of this table when converted to
-     * .class format [including 2 count bytes]
-     */
-    long length ();
-    
-    // Cloneable: adjust the access level of Object.clone():
-    Object clone ();
-
-
-    // MUTATORS:
-
-    /**
-     * Appends a new exception class pointer to the collection. No duplicate checks
-     * are made.
-     * 
-     * @param exception_index constant pool index [must be positive; input not validated]
-     * @return offset of the new pointer [same as {@link #size()}-1 when called
-     * after this method] 
-     */
-    int add (int exception_index);
-    
-    /**
-     * Replaces exception class pointer number 'offset' with new value 'interface_index'.
-     * No duplicate checks are made. It is the responsibility of the caller to
-     * ensure that the relevant CONSTANT_Class_info descriptor will be found
-     * in the constant pool, in the slot pointed to by 'exception_index'.
-     * 
-     * @param offset thrown exception class number [must be in [0, size()) range]
-     * @param exception_index constant pool index [must be positive; input not validated]
-     * @return previous value at the given index [always positive]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    int set (int offset, int exception_index);
-    
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/IExceptionHandlerTable.java b/core/java12/com/vladium/jcd/cls/attribute/IExceptionHandlerTable.java
deleted file mode 100644
index 572ac27..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/IExceptionHandlerTable.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IExceptionHandlerTable.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import com.vladium.jcd.compiler.IClassFormatOutput;
-
-// ----------------------------------------------------------------------------
-/**
- * This table is a structure nested within the {@link CodeAttribute_info}.
- * It is a table of {@link Exception_info} entries, each entry representing an
- * exception handler range. The order of these entries is the order in which
- * a JVM will check for a matching exception handler when the parent method
- * throws an exception.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IExceptionHandlerTable extends Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-
-    // ACCESSORS:
-    
-    /**
-     * Returns {@link Exception_info} descriptor at a given offset.
-     * 
-     * @param offset exception offset [must be in [0, size()) range; input not checked]
-     * @return Exception_info descriptor [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    Exception_info get (int offset);
-    
-    /**
-     * Returns the number of descriptors in this collection [can be 0].
-     */
-    int size ();
-    
-    /**
-     * Returns the total length of this table when converted to
-     * .class format [including 2 count bytes]
-     */
-    long length ();
-    
-    // Cloneable: adjust the access level of Object.clone():
-    Object clone ();
-
-
-    // MUTATORS:
-    
-    /**
-     * Adds a new Exception_info descriptor to this collection. No duplicate
-     * checks are made. It is the responsibility of the caller to ensure
-     * that all data referenced in 'exception' will eventually be consistent
-     * with method's bytecode and the class's constant pool.
-     * 
-     * @param exception new exception descriptor [may not be null]
-     */
-    int add (Exception_info exception);
-    
-    /**
-     * Replaces the Exception_info descriptor at a given offset. No duplicate
-     * checks are made. No exception type compatibility checks are made. It is
-     * the responsibility of the caller to ensure that all data referenced
-     * in 'exception' will eventually be consistent with method's bytecode and
-     * the class's constant pool.
-     * 
-     * @param offset exception offset [must be in [0, size()) range; input not checked]
-     * @param exception new exception descriptor [may not be null]
-     * @return previous exception descriptor at this offset [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    Exception_info set (int offset, Exception_info exception);
-    
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/attribute/InnerClass_info.java b/core/java12/com/vladium/jcd/cls/attribute/InnerClass_info.java
deleted file mode 100644
index 6347a3a..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/InnerClass_info.java
+++ /dev/null
@@ -1,90 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: InnerClass_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.compiler.IClassFormatOutput;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class InnerClass_info implements Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-    
-    public int m_outer_class_index, m_inner_class_index;
-    public int m_inner_name_index;
-    public int m_inner_access_flags;
-    
-    
-    public InnerClass_info (final int outer_class_index, final int inner_class_index,
-                            final int inner_name_index, final int inner_access_flags) 
-    {
-        m_outer_class_index = outer_class_index;
-        m_inner_class_index = inner_class_index;
-        m_inner_name_index = inner_name_index;
-        m_inner_access_flags = inner_access_flags;
-    }
-    
-    
-    public String toString ()
-    {
-        return "innerclass_info: [m_outer_class_index = " + m_outer_class_index + ", m_inner_class_index = " + m_inner_class_index +
-            ", m_inner_name_index = " + m_inner_name_index + ", m_inner_access_flags = " + m_inner_access_flags + "]"; 
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {    
-            return super.clone ();
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }        
-    }
-
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        out.writeU2 (m_inner_class_index);
-        out.writeU2 (m_outer_class_index);
-        out.writeU2 (m_inner_name_index);
-        out.writeU2 (m_inner_access_flags);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    InnerClass_info (final UDataInputStream bytes) throws IOException
-    {
-        m_inner_class_index = bytes.readU2 ();
-        m_outer_class_index = bytes.readU2 ();
-        m_inner_name_index = bytes.readU2 ();
-        m_inner_access_flags = bytes.readU2 ();
-    }
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/jcd/cls/attribute/InnerClassesAttribute_info.java b/core/java12/com/vladium/jcd/cls/attribute/InnerClassesAttribute_info.java
deleted file mode 100644
index 4f24b05..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/InnerClassesAttribute_info.java
+++ /dev/null
@@ -1,164 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: InnerClassesAttribute_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class InnerClassesAttribute_info extends Attribute_info
-{
-    // public: ................................................................
-    
-    // ACCESSORS:
-    
-    public boolean makesClassNested (final int class_index, final int [] nestedAccessFlags)
-    {
-        if (class_index > 0)
-        {
-            // TODO: avoid linear loop by keeping all class indices in a bitset
-            
-            for (int i = 0, iLimit = size (); i < iLimit; ++ i)
-            {
-                final InnerClass_info info = get (i);
-                
-                if (info.m_inner_class_index == class_index)
-                {
-                    nestedAccessFlags [0] = info.m_inner_access_flags;
-                    return true;
-                }
-            }
-        }
-        
-        return false;
-    }
-    
-    /**
-     * Returns {@link InnerClass_info} descriptor at a given offset.
-     * 
-     * @param offset inner class entry offset [must be in [0, size()) range;
-     * input not checked]
-     * @return InnerClass_info descriptor [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    public final InnerClass_info get (final int offset)
-    {
-        return (InnerClass_info) m_classes.get (offset);
-    }
-    
-    /**
-     * Returns the number of descriptors in this collection [can be 0].
-     */
-    public final int size ()
-    {
-        return m_classes.size ();
-    }
-    
-    public final long length ()
-    {
-        return 8 + (m_classes.size () << 3); // use size() if class becomes non-final
-    }
-    
-    // Visitor:
-    
-    public void accept (final IAttributeVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        final StringBuffer s = new StringBuffer ("InnerClassesAttribute_info: [attribute_name_index = " + m_name_index + ", attribute_length = " + length () + "]\n");
-
-        for (int l = 0; l < size (); ++ l)
-        {
-            s.append ("            " + get (l));
-            s.append ("\n"); // TODO: proper EOL const
-        }
-        
-        return s.toString ();
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        final InnerClassesAttribute_info _clone = (InnerClassesAttribute_info) super.clone ();
-        
-        final List/* InnerClass_info */ classes = m_classes;
-        
-        // do deep copy:
-        final int class_count = classes.size (); // use size() if class becomes non-final
-        _clone.m_classes = new ArrayList (class_count);
-        for (int e = 0; e < class_count; ++ e)
-        {
-            _clone.m_classes.add (((InnerClass_info) classes.get (e)).clone ());
-        }
-        
-        return _clone;
-    }
-
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        final List/* InnerClass_info */ classes = m_classes;
-        
-        final int class_count = classes.size (); // use size() if class becomes non-final
-        out.writeU2 (class_count);
-        
-        for (int l = 0; l < class_count; ++ l)
-        {
-            ((InnerClass_info) classes.get (l)).writeInClassFormat (out);
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    InnerClassesAttribute_info (final int attribute_name_index, final long attribute_length,
-                                final UDataInputStream bytes)
-        throws IOException
-    {
-        super (attribute_name_index, attribute_length);
-        
-        final int class_count = bytes.readU2 ();
-        final List/* InnerClass_info */ classes = new ArrayList (class_count);
-        
-        for (int i = 0; i < class_count; ++ i)
-        {
-            classes.add (new InnerClass_info (bytes));
-        }
-        
-        m_classes = classes;
-    }
-    
-    // private: ...............................................................
-    
-    
-    private List/* InnerClass_info */ m_classes; // never null
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/jcd/cls/attribute/LineNumberTableAttribute_info.java b/core/java12/com/vladium/jcd/cls/attribute/LineNumberTableAttribute_info.java
deleted file mode 100644
index 8544167..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/LineNumberTableAttribute_info.java
+++ /dev/null
@@ -1,185 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: LineNumberTableAttribute_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.List;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The LineNumberTable attribute is an optional variable-length attribute in
- * the attributes table of a {@link CodeAttribute_info} attribute. It may be
- * used by debuggers to determine which part of the JVM code array corresponds
- * to a given line number in the original source file. If LineNumberTable
- * attributes are present in the attributes table of a given Code attribute,
- * then they may appear in any order. Furthermore, multiple LineNumberTable
- * attributes may together represent a given line of a source file; that is,
- * LineNumberTable attributes need not be one-to-one with source lines.<P>
- * 
- * The LineNumberTable attribute has the following format:
- * <PRE>
- * LineNumberTable_attribute {
- *          u2 attribute_name_index;
- *          u4 attribute_length;
- *          u2 line_number_table_length;
- *          {  u2 start_pc;             
- *             u2 line_number;             
- *          } line_number_table[line_number_table_length];
- *  }
- * <PRE>
- * 
- * LineNumberTable_attribute structure contains the following items:
- * <PRE>
- *    line_number_table_length
- * </PRE>
- * The value of the line_number_table_length item indicates the number of
- * entries in the line_number_table array.
- * <PRE>
- *    line_number_table[]
- * </PRE>
- * Each entry in the line_number_table array indicates that the line number
- * in the original source file changes at a given point in the code array.<P>
- * 
- * Each line_number_table entry must contain the following two items:
- * <PRE>
- *    start_pc
- * </PRE>
- * The value of the start_pc item must indicate the index into the code array
- * at which the code for a new line in the original source file begins. The
- * value of start_pc must be less than the value of the code_length item of
- * the {@link CodeAttribute_info} attribute of which this LineNumberTable
- * is an attribute.<P>
- * <PRE>
- *    line_number
- * </PRE>
- * The value of the line_number item must give the corresponding line number
- * in the original source file.
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class LineNumberTableAttribute_info extends Attribute_info
-{
-    // public: ................................................................
-    
-    // ACCESSORS:
-    
-    /**
-     * Returns {@link LineNumber_info} descriptor at a given offset.
-     * 
-     * @param offset line number entry offset [must be in [0, size()) range;
-     * input not checked]
-     * @return LineNumber_info descriptor [never null]
-     * 
-     * @throws IndexOutOfBoundsException if 'offset' is outside of valid range
-     */
-    public LineNumber_info get (final int offset)
-    {
-        return (LineNumber_info) m_lines.get (offset);
-    }
-    
-    /**
-     * Returns the number of descriptors in this collection [can be 0].
-     */
-    public int size ()
-    {
-        return m_lines.size ();
-    }
-    
-    public long length ()
-    {
-        return 8 + (m_lines.size () << 2); // use size() if class becomes non-final
-    }
-    
-    // Visitor:
-    
-    public void accept (final IAttributeVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        final StringBuffer s = new StringBuffer ("LineNumberTableAttribute_info: [attribute_name_index = " + m_name_index + ", attribute_length = " + length () + "]\n");
-
-        for (int l = 0; l < size (); ++ l)
-        {
-            s.append ("            " + get (l));
-            s.append ("\n"); // TODO: proper EOL const
-        }
-        
-        return s.toString ();
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        final LineNumberTableAttribute_info _clone = (LineNumberTableAttribute_info) super.clone ();
-        
-        // do deep copy:
-        final int lines_count = m_lines.size (); // use size() if class becomes non-final
-        _clone.m_lines = new ArrayList (lines_count);
-        for (int e = 0; e < lines_count; ++ e)
-        {
-            _clone.m_lines.add (((LineNumber_info) m_lines.get (e)).clone ());
-        }
-        
-        return _clone;
-    }
-
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        final int lines_count = m_lines.size (); // use size() if class becomes non-final
-        out.writeU2 (lines_count);
-        
-        for (int l = 0; l < lines_count; ++ l)
-        {
-            ((LineNumber_info) m_lines.get (l)).writeInClassFormat (out);
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    LineNumberTableAttribute_info (final int attribute_name_index, final long attribute_length,
-                                   final UDataInputStream bytes)
-        throws IOException
-    {
-        super (attribute_name_index, attribute_length);
-        
-        final int lines_count = bytes.readU2 ();
-        m_lines = new ArrayList (lines_count);
-        
-        for (int i = 0; i < lines_count; i++)
-        {
-            m_lines.add (new LineNumber_info (bytes));
-        }
-    }
-    
-    // private: ...............................................................
-    
-    
-    private List/* LineNumber_info */ m_lines; // never null
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/jcd/cls/attribute/LineNumber_info.java b/core/java12/com/vladium/jcd/cls/attribute/LineNumber_info.java
deleted file mode 100644
index ca91e05..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/LineNumber_info.java
+++ /dev/null
@@ -1,96 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: LineNumber_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.compiler.IClassFormatOutput;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * This class represents a line_number_table entry contained by
- * {@link LineNumberTableAttribute_info} attribute. Each entry contains the
- * following items:
- * <PRE>
- *    start_pc
- * </PRE>
- * The value of the start_pc item must indicate the index into the code array
- * at which the code for a new line in the original source file begins. The
- * value of start_pc must be less than the value of the code_length item of
- * the {@link CodeAttribute_info} attribute of which this LineNumberTable
- * is an attribute.<P>
- * <PRE>
- *    line_number
- * </PRE>
- * The value of the line_number item must give the corresponding line number
- * in the original source file.
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class LineNumber_info implements Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-    
-    public int m_start_pc, m_line_number;
-    
-    
-    public LineNumber_info (final int start_pc, final int line_number)
-    {
-        m_start_pc = start_pc;
-        m_line_number = line_number;
-    }
-    
-    public String toString ()
-    {
-        return "line_number_info: [start_pc = " + m_start_pc + ", line_number = " + m_line_number + "]";
-    }    
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {    
-            return super.clone ();
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }        
-    }
-
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        out.writeU2 (m_start_pc);
-        out.writeU2 (m_line_number);
-    }
-    
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-
-    LineNumber_info (final UDataInputStream bytes) throws IOException
-    {
-        m_start_pc = bytes.readU2 ();
-        m_line_number = bytes.readU2 ();
-    }
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/jcd/cls/attribute/SourceFileAttribute_info.java b/core/java12/com/vladium/jcd/cls/attribute/SourceFileAttribute_info.java
deleted file mode 100644
index a1c1a2d..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/SourceFileAttribute_info.java
+++ /dev/null
@@ -1,97 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: SourceFileAttribute_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.cls.ClassDef;
-import com.vladium.jcd.cls.constant.CONSTANT_Utf8_info;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class SourceFileAttribute_info extends Attribute_info
-{
-    // public: ................................................................
-    
-    
-    public int m_sourcefile_index;
-    
-    
-    public SourceFileAttribute_info (final int attribute_name_index)
-    {
-        super (attribute_name_index, 0);
-    }
-    
-    
-    public long length ()
-    {
-        return 8;
-    }
-    
-    public CONSTANT_Utf8_info getSourceFile (final ClassDef cls)
-    {
-        return (CONSTANT_Utf8_info) cls.getConstants ().get (m_sourcefile_index);
-    }  
-    
-    // Visitor:
-    
-    public void accept (final IAttributeVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        return "SourceFileAttribute_info: [attribute_name_index = " + m_name_index + ", attribute_length = " + m_attribute_length + ']';
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {        
-        return super.clone ();    
-    }
-       
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeU2 (m_sourcefile_index);
-    }
-    
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-
-    SourceFileAttribute_info (final int attribute_name_index, final long attribute_length,
-                              final UDataInputStream bytes)
-        throws IOException
-    {
-        super (attribute_name_index, attribute_length);
-        
-        m_sourcefile_index = bytes.readU2 ();
-    }
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
-
diff --git a/core/java12/com/vladium/jcd/cls/attribute/SyntheticAttribute_info.java b/core/java12/com/vladium/jcd/cls/attribute/SyntheticAttribute_info.java
deleted file mode 100644
index 0266970..0000000
--- a/core/java12/com/vladium/jcd/cls/attribute/SyntheticAttribute_info.java
+++ /dev/null
@@ -1,98 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: SyntheticAttribute_info.java,v 1.1.1.1.2.1 2004/07/10 03:34:52 vlad_r Exp $
- */
-package com.vladium.jcd.cls.attribute;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The Synthetic attribute is a fixed-length attribute in the attributes table
- * of ClassFile, {@link com.vladium.jcd.cls.Field_info}, and
- * {@link com.vladium.jcd.cls.Method_info} structures. A class member that does
- * not appear in the source code must be marked using a Synthetic attribute.<P>
- * 
- * The Synthetic attribute has the following format:
- * <PRE>
- * Synthetic_attribute {
- *          u2 attribute_name_index;
- *          u4 attribute_length;
- * }
- * </PRE>
- * 
- * The value of the attribute_name_index item must be a valid index into the
- * constant_pool table. The constant_pool entry at that index must be a CONSTANT_Utf8_info
- * structure representing the string "Synthetic".<P>
- * 
- * The value of the attribute_length item is zero.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class SyntheticAttribute_info extends Attribute_info
-{
-    // public: ................................................................
-    
-    
-    public SyntheticAttribute_info (final int attribute_name_index)
-    {
-        super (attribute_name_index, 0);
-    }
-    
-    
-    public long length ()
-    {
-        return 6;
-    }
-    
-    // Visitor:
-    
-    public void accept (final IAttributeVisitor visitor, final Object ctx)
-    {
-        visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        return "SyntheticValueAttribute_info: [attribute_name_index = " + m_name_index + ", attribute_length = " + m_attribute_length + ']';
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs a deep copy.
-     */
-    public Object clone ()
-    {        
-        return super.clone ();    
-    }
-       
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-    }
-    
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-
-    SyntheticAttribute_info (final int attribute_name_index, final long attribute_length)
-    {
-        super (attribute_name_index, attribute_length);
-    }
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
-
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Class_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Class_info.java
deleted file mode 100644
index 07984a3..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Class_info.java
+++ /dev/null
@@ -1,98 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_Class_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.cls.ClassDef;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The CONSTANT_Class_info structure is used to represent a class or an interface.<P>
- * 
- * The value of the name_index item must be a valid index into the constant pool
- * table. The constant pool entry at that index must be a {@link CONSTANT_Utf8_info}
- * structure representing a valid fully qualified Java class name that has been
- * converted to the class file's internal form. 
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CONSTANT_Class_info extends CONSTANT_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 7;
-    
-    public int m_name_index;
-    
-    
-    public CONSTANT_Class_info (final int name_index)
-    {
-        m_name_index = name_index;
-    }
-
-    
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    /**
-     * Returns the JVM class name within the constant pool context of 'cls'
-     * class definition.
-     * 
-     * @param cls class that contains this constant
-     * @return class name [in JVM format]
-     */
-    public String getName (final ClassDef cls)
-    {
-        return ((CONSTANT_Utf8_info) cls.getConstants ().get (m_name_index)).m_value;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    } 
-
-    
-    public String toString ()
-    {
-        return "CONSTANT_Class: [name_index = " + m_name_index + ']';
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeU2 (m_name_index);
-    }
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_Class_info (final UDataInputStream bytes) throws IOException
-    {
-        m_name_index = bytes.readU2 ();
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Double_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Double_info.java
deleted file mode 100644
index a662092..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Double_info.java
+++ /dev/null
@@ -1,91 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_Double_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The {@link CONSTANT_Long_info} and CONSTANT_Double_info represent eight-byte
- * numeric (long and double) constants.<P>
- * 
- * The high_bytes and low_bytes items of the CONSTANT_Double_info structure contain
- * the double value in IEEE 754 floating-point "double format" bit layout.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CONSTANT_Double_info extends CONSTANT_literal_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 6;
-    
-    public double m_value;
-    
-    
-    public CONSTANT_Double_info (final double value)
-    {
-        m_value = value;    
-    }
-
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        return Double.toString (m_value);
-    }
-    
-    /**
-     * Overrides the default implementation to return '2'.
-     */
-    public int width ()
-    {
-        return 2;
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeDouble (m_value);
-    }
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_Double_info (final UDataInputStream bytes) throws IOException
-    {
-        m_value = bytes.readDouble ();    
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Fieldref_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Fieldref_info.java
deleted file mode 100644
index 0859227..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Fieldref_info.java
+++ /dev/null
@@ -1,73 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_Fieldref_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * This structure is used in the constant pool to represent dynamic references
- * to fields. The class_index item of a CONSTANT_Fieldref_info or a
- * {@link CONSTANT_Methodref_info} structure must be a class type, not an
- * interface type. 
- * 
- * @see CONSTANT_ref_info
- * @see CONSTANT_Methodref_info
- * @see CONSTANT_InterfaceMethodref_info
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CONSTANT_Fieldref_info extends CONSTANT_ref_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 9;
-    
-    
-    public CONSTANT_Fieldref_info (final int class_index, final int name_and_type_index)
-    {
-        super (class_index, name_and_type_index);
-    }
-
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        return "CONSTANT_Fieldref: [class_index = " + m_class_index + ", name_and_type_index = " + m_name_and_type_index + ']';
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_Fieldref_info (final UDataInputStream bytes) throws IOException
-    {
-        super (bytes);
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Float_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Float_info.java
deleted file mode 100644
index 5d7d27a..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Float_info.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_Float_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The CONSTANT_Integer_info and CONSTANT_Float_info structures represent
- * four-byte numeric (int and float) constants.<P>
- * 
- * The bytes item of the CONSTANT_Float_info structure contains the value of
- * the float constant in IEEE 754 floating-point "single format" bit layout.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CONSTANT_Float_info extends CONSTANT_literal_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 4;
-    
-    public float m_value;
-    
-    
-    public CONSTANT_Float_info (final float value)
-    {
-        m_value = value;
-    }
-
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        return Float.toString (m_value);
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeFloat (m_value);
-    }
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_Float_info (final UDataInputStream bytes) throws IOException
-    {
-        m_value = bytes.readFloat ();
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Integer_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Integer_info.java
deleted file mode 100644
index a6ffe5a..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Integer_info.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_Integer_info.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The CONSTANT_Integer_info and CONSTANT_Float_info structures represent
- * four-byte numeric (int and float) constants.<P>
- * 
- * The bytes item of the CONSTANT_Integer_info structure contains the value of
- * the int constant. The bytes of the value are stored in big-endian (high byte
- * first) order.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CONSTANT_Integer_info extends CONSTANT_literal_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 3;
-    
-    public int m_value;
-    
-    
-    public CONSTANT_Integer_info (final int value)
-    {
-        m_value = value;
-    }
-
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        return Integer.toString (m_value);
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeInt (m_value);
-    }
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_Integer_info (final UDataInputStream bytes) throws IOException
-    {
-        m_value = bytes.readInt ();
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_InterfaceMethodref_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_InterfaceMethodref_info.java
deleted file mode 100644
index 76113c3..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_InterfaceMethodref_info.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_InterfaceMethodref_info.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * This structure is used in the constant pool to represent dynamic references
- * to interface methods. The class_index item of a CONSTANT_InterfaceMethodref_info
- * structure must be an interface type that declares the given method. 
- * 
- * @see CONSTANT_ref_info
- * @see CONSTANT_Fieldref_info
- * @see CONSTANT_Methodref_info
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CONSTANT_InterfaceMethodref_info extends CONSTANT_ref_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 11;
-    
-    
-    public CONSTANT_InterfaceMethodref_info (final int class_index, final int name_and_type_index)
-    {
-        super (class_index, name_and_type_index);
-    }
-
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    }
-        
-    public String toString ()
-    {
-        return "CONSTANT_InterfaceMethodref: [class_index = " + m_class_index + ", name_and_type_index = " + m_name_and_type_index + ']';
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_InterfaceMethodref_info (final UDataInputStream bytes) throws IOException
-    {
-        super (bytes);
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Long_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Long_info.java
deleted file mode 100644
index 22f7bc4..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Long_info.java
+++ /dev/null
@@ -1,92 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_Long_info.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The CONSTANT_Long_info and {@link CONSTANT_Double_info} represent eight-byte
- * numeric (long and double) constants.<P>
- * 
- * The unsigned high_bytes and low_bytes items of the CONSTANT_Long_info structure
- * together contain the value of the long constant
- * (( long ) high_bytes << 32) + low_bytes , where the bytes of each of high_bytes
- * and low_bytes are stored in big-endian (high byte first) order.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CONSTANT_Long_info extends CONSTANT_literal_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 5;
-    
-    public long m_value;
-    
-    
-    public CONSTANT_Long_info (final long value)
-    {
-        m_value = value;
-    }
-
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        return Long.toString (m_value);
-    }
-    
-    /**
-     * Overrides the default implementation to return '2'.
-     */
-    public int width ()
-    {
-        return 2;
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeLong (m_value);
-    }
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_Long_info (final UDataInputStream bytes) throws IOException
-    {
-        m_value = bytes.readLong ();
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Methodref_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Methodref_info.java
deleted file mode 100644
index 149c5cb..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Methodref_info.java
+++ /dev/null
@@ -1,73 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_Methodref_info.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * This structure is used in the constant pool to represent dynamic references
- * to class methods. The class_index item of a {@link CONSTANT_Fieldref_info} or
- * a CONSTANT_Methodref_info structure must be a class type, not an interface type.
- *  
- * @see CONSTANT_ref_info
- * @see CONSTANT_Fieldref_info
- * @see CONSTANT_InterfaceMethodref_info
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CONSTANT_Methodref_info extends CONSTANT_ref_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 10;
-    
-    
-    public CONSTANT_Methodref_info (final int class_index, final int name_and_type_index)
-    {
-        super (class_index, name_and_type_index);
-    }
-
-
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    } 
-    
-    public String toString ()
-    {
-        return "CONSTANT_Methodref_info: [class_index = " + m_class_index + ", name_and_type_index = " + m_name_and_type_index + ']';
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_Methodref_info (final UDataInputStream bytes) throws IOException
-    {
-        super (bytes);
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_NameAndType_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_NameAndType_info.java
deleted file mode 100644
index d27a4f7..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_NameAndType_info.java
+++ /dev/null
@@ -1,104 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_NameAndType_info.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.cls.ClassDef;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The CONSTANT_NameAndType_info structure is used to represent a field or method,
- * without indicating which class or interface type it belongs to.<P>
- * 
- * The value of the name_index item must be a valid index into the constant pool
- * table. The constant pool entry at that index must be a {@link CONSTANT_Utf8_info}
- * structure representing a valid Java field name or method name stored as a simple
- * (not fully qualified) name, that is, as a Java identifier.<P>
- * 
- * The value of the descriptor_index item must be a valid index into the constant
- * pool table. The constant pool entry at that index must be a {@link CONSTANT_Utf8_info}
- * structure representing a valid Java field descriptor or method descriptor.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CONSTANT_NameAndType_info extends CONSTANT_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 12;
-    
-    
-    public int m_name_index;
-    public int m_descriptor_index;
-    
-    
-    public CONSTANT_NameAndType_info (final int name_index, final int descriptor_index)
-    {
-        m_name_index = name_index;
-        m_descriptor_index = descriptor_index;
-    }
-    
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    public String getName (final ClassDef cls)
-    {
-        return ((CONSTANT_Utf8_info) cls.getConstants ().get (m_name_index)).m_value;
-    }
-    
-    public String getDescriptor (final ClassDef cls)
-    {
-        return ((CONSTANT_Utf8_info) cls.getConstants ().get (m_descriptor_index)).m_value;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    }
-     
-    public String toString ()
-    {
-        return "CONSTANT_NameAndType: [name_index = " + m_name_index + ", descriptor_index = " + m_descriptor_index + ']';
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeU2 (m_name_index);
-        out.writeU2 (m_descriptor_index);
-    }
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_NameAndType_info (final UDataInputStream bytes) throws IOException
-    {
-        m_name_index = bytes.readU2 ();
-        m_descriptor_index = bytes.readU2 ();
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_String_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_String_info.java
deleted file mode 100644
index 82f495a..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_String_info.java
+++ /dev/null
@@ -1,85 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_String_info.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The CONSTANT_String_info structure is used to represent constant objects of
- * the type java.lang.String.<P>
- * 
- * The value of the string_index item must be a valid index into the constant pool
- * table. The constant pool entry at that index must be a {@link CONSTANT_Utf8_info}
- * structure representing the sequence of characters to which the
- * java.lang.String object is to be initialized.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public 
-final class CONSTANT_String_info extends CONSTANT_literal_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 8;
-    
-    public int m_string_index;
-    
-    
-    public CONSTANT_String_info (final int string_index)
-    {
-        m_string_index = string_index;
-    }
-
-
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    }
-    
-    public String toString ()
-    {
-        return "CONSTANT_String: [string_index = " + m_string_index + ']';
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeU2 (m_string_index);    
-    }
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_String_info (final UDataInputStream bytes) throws IOException
-    {
-        m_string_index = bytes.readU2 ();
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Utf8_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Utf8_info.java
deleted file mode 100644
index 5d2eaf1..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_Utf8_info.java
+++ /dev/null
@@ -1,87 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_Utf8_info.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * The CONSTANT_Utf8_info structure is used to represent constant string values.<P>
- * 
- * The bytes of multibyte characters are stored in the class file in big-endian
- * (high byte first) order. There are two differences between this format and the
- * "standard" UTF-8 format. First, the null byte (byte)0 is encoded using the
- * two-byte format rather than the one-byte format, so that Java Virtual Machine
- * UTF-8 strings never have embedded nulls. Second, only the one-byte, two-byte,
- * and three-byte formats are used. The Java Virtual Machine does not recognize
- * the longer UTF-8 formats.  
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class CONSTANT_Utf8_info extends CONSTANT_info
-{
-    // public: ................................................................
-
-    public static final byte TAG = 1;
-    
-    public String m_value;
-    
-    
-    public CONSTANT_Utf8_info (final String value)
-    {
-        m_value = value;
-    }
-
-
-    public final byte tag ()
-    {
-        return TAG;
-    }
-    
-    // Visitor:
-    
-    public Object accept (final ICONSTANTVisitor visitor, final Object ctx)
-    {
-        return visitor.visit (this, ctx);
-    } 
-    
-    public String toString ()
-    {
-        return "CONSTANT_Utf8: [" + m_value + ']';
-    }
-       
-    // Cloneable: inherited clone() is Ok
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeUTF (m_value);
-    }
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_Utf8_info (final UDataInputStream bytes) throws IOException
-    {
-        m_value = bytes.readUTF ();
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_info.java
deleted file mode 100644
index c078847..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_info.java
+++ /dev/null
@@ -1,203 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_info.java,v 1.1.1.1 2004/05/09 16:57:48 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.compiler.IClassFormatOutput;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * An abstract base for all other CONSTANT_XXX_info structures. See $4.4 in VM
- * spec 1.0 for all such structure definitions.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-abstract class CONSTANT_info implements Cloneable, IClassFormatOutput
-{
-    // public: ................................................................
-    
-    
-    /**
-     * Returns the tag byte for this CONSTANT type [this data is
-     * static class data].
-     */
-    public abstract byte tag ();
-    
-    // Visitor:
-    
-    public abstract Object accept (ICONSTANTVisitor visitor, Object ctx); 
-    
-    public abstract String toString ();
-    
-    /**
-     * Returns the number of constant pool index slots occupied by this
-     * CONSTANT type. This implementation defaults to returning '1'.
-     * 
-     * @see CONSTANT_Long_info
-     * @see CONSTANT_Long_info
-     * 
-     * @return int
-     */
-    public int width ()
-    {
-        return 1;
-    }
-    
-    
-    /**
-     * Virtual constructor method for all CONSTANT_XXX_info structures.
-     */
-    public static CONSTANT_info new_CONSTANT_info (final UDataInputStream bytes)
-        throws IOException
-    {
-        byte tag = bytes.readByte ();                                                                                   
-        
-        switch (tag)
-        {
-        case CONSTANT_Utf8_info.TAG:
-            return new CONSTANT_Utf8_info (bytes);
-            
-        case CONSTANT_Integer_info.TAG:
-            return new CONSTANT_Integer_info (bytes);
-            
-        case CONSTANT_Float_info.TAG:
-            return new CONSTANT_Float_info (bytes);
-            
-        case CONSTANT_Long_info.TAG:
-            return new CONSTANT_Long_info (bytes);
-            
-        case CONSTANT_Double_info.TAG:
-            return new CONSTANT_Double_info (bytes);
-        
-            
-        case CONSTANT_Class_info.TAG:
-            return new CONSTANT_Class_info (bytes);
-            
-        case CONSTANT_String_info.TAG:
-            return new CONSTANT_String_info (bytes);
-            
-            
-        case CONSTANT_Fieldref_info.TAG:
-            return new CONSTANT_Fieldref_info (bytes);
-            
-        case CONSTANT_Methodref_info.TAG:
-            return new CONSTANT_Methodref_info (bytes);
-            
-        case CONSTANT_InterfaceMethodref_info.TAG:
-            return new CONSTANT_InterfaceMethodref_info (bytes);
-            
-            
-        case CONSTANT_NameAndType_info.TAG:
-            return new CONSTANT_NameAndType_info (bytes);
-            
-        default: throw new IllegalStateException ("CONSTANT_info: invalid tag value [" + tag + ']');
-                 
-        } // end of switch
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Chains to super.clone() and removes CloneNotSupportedException
-     * from the method signature.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            return super.clone ();
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }
-    }
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {    
-        out.writeByte (tag ());
-    }
-    
-    public static String tagToString (final CONSTANT_info constant)
-    {
-        switch (constant.tag ())
-        {
-        case CONSTANT_Utf8_info.TAG:
-            return "CONSTANT_Utf8";
-            
-        case CONSTANT_Integer_info.TAG:
-            return "CONSTANT_Integer";
-            
-        case CONSTANT_Float_info.TAG:
-            return "CONSTANT_Float";
-            
-        case CONSTANT_Long_info.TAG:
-            return "CONSTANT_Long";
-            
-        case CONSTANT_Double_info.TAG:
-            return "CONSTANT_Double";
-        
-            
-        case CONSTANT_Class_info.TAG:
-            return "CONSTANT_Class";
-            
-        case CONSTANT_String_info.TAG:
-            return "CONSTANT_String";
-            
-            
-        case CONSTANT_Fieldref_info.TAG:
-            return "CONSTANT_Fieldref";
-            
-        case CONSTANT_Methodref_info.TAG:
-            return "CONSTANT_Methodref";
-            
-        case CONSTANT_InterfaceMethodref_info.TAG:
-            return "CONSTANT_InterfaceMethodref";
-            
-            
-        case CONSTANT_NameAndType_info.TAG:
-            return "CONSTANT_NameAndType";
-            
-        default: throw new IllegalStateException ("CONSTANT_info: invalid tag value [" + constant.tag () + ']');
-                 
-        } // end of switch
-    }
-    
-    // protected: .............................................................
-
-    /*
-    protected static final byte CONSTANT_Utf8                       = 1;
-    protected static final byte CONSTANT_Integer                    = 3;
-    protected static final byte CONSTANT_Float                      = 4;
-    protected static final byte CONSTANT_Long                       = 5;
-    protected static final byte CONSTANT_Double                     = 6;
-    protected static final byte CONSTANT_Class                      = 7;
-    protected static final byte CONSTANT_String                     = 8;
-    protected static final byte CONSTANT_Fieldref                   = 9;
-    protected static final byte CONSTANT_Methodref                  = 10;
-    protected static final byte CONSTANT_InterfaceMethodref         = 11;
-    protected static final byte CONSTANT_NameAndType                = 12;
-    */
-    
-    protected CONSTANT_info ()
-    {
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_literal_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_literal_info.java
deleted file mode 100644
index 316526c..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_literal_info.java
+++ /dev/null
@@ -1,43 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_literal_info.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-// ----------------------------------------------------------------------------
-/**
- * Abstract base for all CONSTANT_XXX_info structures representing literal values
- * in the constant pool.
- * 
- * @see CONSTANT_Integer_info
- * @see CONSTANT_Long_info
- * @see CONSTANT_Float_info
- * @see CONSTANT_Double_info
- * @see CONSTANT_String_info
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-abstract class CONSTANT_literal_info extends CONSTANT_info
-{
-    // public: ................................................................
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_literal_info ()
-    {
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_ref_info.java b/core/java12/com/vladium/jcd/cls/constant/CONSTANT_ref_info.java
deleted file mode 100644
index 1ffd7a5..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/CONSTANT_ref_info.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CONSTANT_ref_info.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * Abstract base for all CONSTANT_XXXref_info structures. They all have a constant
- * pool pointer to a {@link CONSTANT_Class_info} and {@link CONSTANT_NameAndType_info}
- * entries.<P>
- * 
- * The value of the class_index item must be a valid index into the constant pool
- * table. The constant pool entry at that index must be a {@link CONSTANT_Class_info}
- * structure representing the class or interface type that contains the declaration
- * of the field or method.<P>
- * 
- * The class_index item of a {@link CONSTANT_Fieldref_info} or a {@link CONSTANT_Methodref_info}
- * structure must be a class type, not an interface type. The class_index item of
- * a {@link CONSTANT_InterfaceMethodref_info} structure must be an interface type
- * that declares the given method.
- *
- * @see CONSTANT_Fieldref_info
- * @see CONSTANT_Methodref_info
- * @see CONSTANT_InterfaceMethodref_info
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-abstract class CONSTANT_ref_info extends CONSTANT_info
-{
-    // public: ................................................................
-
-    
-    public int m_class_index;
-    public int m_name_and_type_index;
-    
-    // IClassFormatOutput:
-    
-    public void writeInClassFormat (final UDataOutputStream out) throws IOException
-    {
-        super.writeInClassFormat (out);
-        
-        out.writeU2 (m_class_index);
-        out.writeU2 (m_name_and_type_index);
-    }
-    
-    // Cloneable: inherited clone() is Ok
-    
-    // protected: .............................................................
-
-    
-    protected CONSTANT_ref_info (final UDataInputStream bytes)
-        throws IOException
-    {
-        m_class_index = bytes.readU2 ();
-        m_name_and_type_index = bytes.readU2 ();
-    }
-    
-    protected CONSTANT_ref_info (final int class_index, final int name_and_type_index)
-    {
-        m_class_index = class_index;
-        m_name_and_type_index = name_and_type_index;
-    }
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/cls/constant/ICONSTANTVisitor.java b/core/java12/com/vladium/jcd/cls/constant/ICONSTANTVisitor.java
deleted file mode 100644
index c6f0d22..0000000
--- a/core/java12/com/vladium/jcd/cls/constant/ICONSTANTVisitor.java
+++ /dev/null
@@ -1,38 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ICONSTANTVisitor.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.cls.constant;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface ICONSTANTVisitor
-{
-    // public: ................................................................
-    
-    //Object visit (CONSTANT_info constant, Object ctx);
-    
-    Object visit (CONSTANT_Class_info constant, Object ctx);
-    
-    Object visit (CONSTANT_InterfaceMethodref_info constant, Object ctx);
-    Object visit (CONSTANT_Methodref_info constant, Object ctx);
-    Object visit (CONSTANT_Fieldref_info constant, Object ctx);
-
-    Object visit (CONSTANT_Double_info constant, Object ctx);
-    Object visit (CONSTANT_Float_info constant, Object ctx);
-    Object visit (CONSTANT_Integer_info constant, Object ctx);
-    Object visit (CONSTANT_Long_info constant, Object ctx);
-    Object visit (CONSTANT_String_info constant, Object ctx);
-
-    Object visit (CONSTANT_Utf8_info constant, Object ctx);
-    Object visit (CONSTANT_NameAndType_info constant, Object ctx);
-
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/compiler/ClassWriter.java b/core/java12/com/vladium/jcd/compiler/ClassWriter.java
deleted file mode 100644
index 6154b66..0000000
--- a/core/java12/com/vladium/jcd/compiler/ClassWriter.java
+++ /dev/null
@@ -1,40 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ClassWriter.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.compiler;
-
-import java.io.IOException;
-import java.io.OutputStream;
-
-import com.vladium.jcd.cls.*;
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-abstract class ClassWriter
-{
-    // public: ................................................................
-    
-
-    public static void writeClassTable (final ClassDef classTable, final OutputStream out)
-        throws IOException
-    {
-        classTable.writeInClassFormat (new UDataOutputStream (out));
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/compiler/CodeGen.java b/core/java12/com/vladium/jcd/compiler/CodeGen.java
deleted file mode 100644
index c561f4e..0000000
--- a/core/java12/com/vladium/jcd/compiler/CodeGen.java
+++ /dev/null
@@ -1,133 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: CodeGen.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.compiler;
-
-import com.vladium.jcd.cls.ClassDef;
-import com.vladium.jcd.cls.constant.CONSTANT_Integer_info;
-import com.vladium.jcd.opcodes.IOpcodes;
-import com.vladium.util.ByteArrayOStream;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class CodeGen implements IOpcodes
-{
-    // public: ................................................................
-    
-    
-    public static void load_local_object_var (final ByteArrayOStream out, final int index)
-    {
-        if (index <= 3)
-        {
-            out.write (_aload_0 + index); // aload_n
-        }
-        else if (index <= 0xFF)
-        {
-            out.write2 (_aload,
-                        index);  // indexbyte
-        }
-        else
-        {
-            out.write4 (_wide,
-                        _aload,
-                        index >>> 8,    // indexbyte1
-                        index);         // indexbyte2
-        }
-    }
-    
-    public static void store_local_object_var (final ByteArrayOStream out, final int index)
-    {
-        if (index <= 3)
-        {
-            out.write (_astore_0 + index); // astore_n
-        }
-        else if (index <= 0xFF)
-        {
-            out.write2 (_astore,
-                        index);  // indexbyte
-        }
-        else
-        {
-            out.write4 (_wide,
-                        _astore,
-                        index >>> 8,    // indexbyte1
-                        index);         // indexbyte2
-        }
-        
-        // [stack -1]
-    }
-    
-    public static void push_int_value (final ByteArrayOStream out, final ClassDef cls, final int value)
-    {
-        if ((-1 <= value) && (value <= 5))
-        {
-            out.write (_iconst_0 + value);
-        }
-        else if ((-128 <= value) && (value <= 127))
-        {
-            out.write2 (_bipush,
-                        value); // byte1
-        }
-        else if ((-32768 <= value) && (value <= 32767))
-        {
-            out.write3 (_sipush,
-                        value >>> 8,    // byte1
-                        value);         // byte2
-        }
-        else // we have to create an Integer constant in the constant pool:
-        {
-            // TODO: check if it's already there
-            final int index = cls.getConstants ().add (new CONSTANT_Integer_info (value));
-            
-            if (index <= 0xFF)
-            {
-                out.write2 (_ldc,
-                            index);  // index
-            }
-            else // must use ldc_w
-            {
-                out.write3 (_ldc_w,
-                            index >>> 8,  // indexbyte1
-                            index);       // indexbyte2
-            }
-        }
-        
-        // [stack +1]
-    }
-    
-    public static void push_constant_index (final ByteArrayOStream out, final int index)
-    {
-        if (index <= 0xFF)
-        {
-            out.write2 (_ldc,
-                       index);  // indexbyte
-        }
-        else
-        {
-            out.write3 (_ldc_w,
-                        index >>> 8,     // indexbyte1
-                        index);          // indexbyte2
-        }
-        
-        // [stack +1]
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private CodeGen () {} // prevent subclassing
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/compiler/IClassFormatOutput.java b/core/java12/com/vladium/jcd/compiler/IClassFormatOutput.java
deleted file mode 100644
index 0e70540..0000000
--- a/core/java12/com/vladium/jcd/compiler/IClassFormatOutput.java
+++ /dev/null
@@ -1,30 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IClassFormatOutput.java,v 1.1.1.1 2004/05/09 16:57:49 vlad_r Exp $
- */
-package com.vladium.jcd.compiler;
-
-import java.io.IOException;
-
-import com.vladium.jcd.lib.UDataOutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * Our class tables and nested table structures support this interface so that
- * they could be serialized into binary format as per .class layout format.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-interface IClassFormatOutput
-{
-    // public: ................................................................
-
-    void writeInClassFormat (UDataOutputStream out) throws IOException;
-    
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/lib/Types.java b/core/java12/com/vladium/jcd/lib/Types.java
deleted file mode 100644
index 05b4230..0000000
--- a/core/java12/com/vladium/jcd/lib/Types.java
+++ /dev/null
@@ -1,756 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Types.java,v 1.1.1.1 2004/05/09 16:57:50 vlad_r Exp $
- */
-package com.vladium.jcd.lib;
-
-import java.io.IOException;
-import java.lang.reflect.*;
-
-import com.vladium.jcd.cls.IAccessFlags;
-
-// ----------------------------------------------------------------------------
-/**
- * Utility methods for manipulating type signatures and descriptors.
- * 
- * TODO: fix usage of chars in parsers
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public abstract class Types
-{
-    // public: ................................................................
-    
-    /**
-     * Returns 'c''s package name [does not include trailing '.'] or ""
-     * if 'c' is in the default package.
-     */
-    public static String getClassPackageName (final Class c)
-    {
-        // TODO: handle array and other types
-        
-        final String className = c.getName ();
-        final int lastDot = className.lastIndexOf ('.');
-        return lastDot >= 0 ? className.substring (0, lastDot) : "";
-    }
-    
-    
-    public static String accessFlagsToString (final int flags, final boolean isClass)
-    {
-        final StringBuffer result = new StringBuffer ();
-      
-        boolean first = true;
-        
-        if (isClass)
-        {
-            for (int f = 0; f < IAccessFlags.ALL_ACC.length; ++ f)
-            {
-                final int bit = IAccessFlags.ALL_ACC [f];
-                
-                if ((flags & bit) != 0)
-                {
-                    if (first)
-                        first = false;
-                    else
-                        result.append (" ");
-                    
-                    if (bit == IAccessFlags.ACC_SUPER)
-                        result.append ("super");
-                    else
-                        result.append (IAccessFlags.ALL_ACC_NAMES [f]);
-                }
-            }
-        }
-        else
-        {
-            for (int f = 0; f < IAccessFlags.ALL_ACC.length; ++ f)
-            {
-                final int bit = IAccessFlags.ALL_ACC [f];
-                
-                if ((flags & bit) != 0)
-                {
-                    if (first)
-                        first = false;
-                    else
-                        result.append (" ");
-                        
-                    result.append (IAccessFlags.ALL_ACC_NAMES [f]);
-                }
-            }
-        }
-        
-        return result.toString ();
-    } 
-
-    
-    /**
-     * Converts Java-styled package/class name to how it would be
-     * represented in the VM.<P>
-     * 
-     * Example:<BR>
-     * javaNameToVMName("java.lang.Object") = "java/lang/Object"
-     * 
-     * @see #vmNameToJavaName
-     */
-    public static String javaNameToVMName (final String javaName)
-    {
-        if (javaName == null) return null;
-        return javaName.replace ('.', '/');
-    }
-    
-    
-    /**
-     * Converts a VM-styled package/class name to how it would be
-     * represented in Java.<P>
-     * 
-     * Example:<BR>
-     * vmNameToJavaName("java/lang/Object") = "java.lang.Object"
-     * 
-     * @see #javaNameToVMName
-     */
-    public static String vmNameToJavaName (final String vmName)
-    {
-        if (vmName == null) return null;
-        return vmName.replace ('/', '.');
-    }
-    
-    
-    /**
-     * Converts a method signature to its VM descriptor representation.
-     * See $4.3 of the VM spec 1.0 for the descriptor grammar.<P>
-     * 
-     * Example:<BR>
-     * signatureToDescriptor(new Object().getClass().getMethod("equals" ,new Class[0])) = "(Ljava/lang/Object;)Z"
-     * <P>
-     * 
-     * Equivalent to
-     * <CODE>signatureToDescriptor(method.getParameterTypes (), method.getReturnType ())</CODE>.
-     */
-    public static String signatureToDescriptor (Method method)
-    {
-        if (method == null) throw new IllegalArgumentException ("null input: method");
-        return signatureToDescriptor (method.getParameterTypes (), method.getReturnType ());
-    }
-    
-    
-    /**
-     * Converts a method signature (parameter types + return type) to its VM descriptor
-     * representation. See $4.3 of the VM spec 1.0 for the descriptor grammar.<P>
-     */
-    public static String signatureToDescriptor (Class [] parameterTypes, Class returnType)
-    {
-        return new signatureCompiler ().signatureDescriptor (parameterTypes, returnType);
-    }
-    
-    
-    /**
-     * Converts a type (a Class) to its VM descriptor representation.<P>
-     * 
-     * Example:<BR>
-     * typeToDescriptor(Object.class) = "Ljava/lang/Object;" <BR>
-     * typeToDescriptor(boolean.class) = "Z"
-     * <P>
-     * Note the invariant typeToDescriptor(descriptorToType(desc)) == desc.
-     * 
-     * @see #descriptorToType
-     */
-    public static String typeToDescriptor (Class type)
-    {
-        return new signatureCompiler ().typeDescriptor (type);
-    }
-    
-    
-    /**
-     * Converts a VM descriptor to the corresponding type.<P>
-     * 
-     * Example:<BR>
-     * descriptorToType("[[I") = int[][].class <BR>
-     * descriptorToType("B") = byte.class
-     * <P>
-     * Note the invariant descriptorToType(typeToDescriptor(c)) == c.
-     * 
-     * @see #descriptorToType
-     */
-    public static Class descriptorToType (String typedescriptor) throws ClassNotFoundException
-    {
-        return new typeDescriptorCompiler ().descriptorToClass (typedescriptor);
-    }
-    
-    
-    
-    public static String descriptorToReturnType (String methoddescriptor)
-    {
-        final int i1 = methoddescriptor.indexOf ('(');
-        final int i2 = methoddescriptor.lastIndexOf (')');
-        
-        if ((i1 < 0) || (i2 <= 0) || (i1 >= i2) || (i2 >= methoddescriptor.length () - 1))
-            throw new IllegalArgumentException ("malformed method descriptor: [" + methoddescriptor + "]");
-
-        return methoddescriptor.substring (i2 + 1);                                                                                                
-    }
-    
-    
-    public static String [] descriptorToParameterTypes (String methoddescriptor)
-    {
-        //System.out.println ("METHOD DESCRIPTOR: [" + methoddescriptor + "]");
-    
-        try
-        {
-            final methodDescriptorCompiler compiler = new methodDescriptorCompiler (methoddescriptor);
-            compiler.methodDescriptor ();
-            return compiler.getResult ();
-        }
-        catch (IOException e)
-        {
-            throw new IllegalArgumentException ("error parsing [" + methoddescriptor + "]: " + e.toString ());
-        }
-        
-        /*
-        final java.util.Vector _result = new java.util.Vector ();
-        final StringBuffer token = new StringBuffer ();
-
-        char c = '*';
-        int scan = 0;
-        
-        for (int state = 0; state != 4; )
-        {
-            try
-            {
-                switch (state)
-                {
-                case 0:
-                    c = methoddescriptor.charAt (scan++);
-                    if (c == '(')
-                        state = 1;
-                    else
-                        throw new IllegalArgumentException ("malformed method descriptor: [" + methoddescriptor + "]");
-                    break;
-                    
-                case 1:
-                    c = methoddescriptor.charAt (scan);
-                    switch (c)
-                    {
-                    case 'B':
-                    case 'C':
-                    case 'D':
-                    case 'F':
-                    case 'I':
-                    case 'J':
-                    case 'S':
-                    case 'Z':
-                        token.append (c);
-                        _result.addElement (token.toString ());
-                        token.setLength (0);
-                        scan++;
-                        break;
-                        
-                    case 'L':
-                        state = 2;
-                        token.append (c);
-                        scan++;
-                        break;
-                        
-                    case '[':
-                        state = 3;    
-                        token.append (c);
-                        scan++;
-                        break;
-                        
-                    case ')':
-                        if (token.length () > 0)
-                        {
-                            _result.addElement (token.toString ());
-                            token.setLength (0);
-                        }
-                        state = 4;
-                        break;
-                            
-                        
-                    default:
-                        throw new IllegalArgumentException ("[state = " + state + ", c = " + c + "] malformed method descriptor: [" + methoddescriptor + "]");
-                        
-                    } // end of nested switch
-                    break;
-                    
-                case 2:
-                    c = methoddescriptor.charAt (scan++);
-                    token.append (c);
-                    if (c == ';')
-                    {
-                        _result.addElement (token.toString ());
-                        token.setLength (0);
-                        state = 1;
-                    }
-                    break;
-                    
-                case 3:
-                    c = methoddescriptor.charAt (scan++);
-                    token.append (c);
-                    if (c != '[')
-                    {
-                        state = 1;
-                    }
-                    break;    
-                    
-                } // end of switch
-                
-                //System.out.println ("[state = " + state + ", c = " + c + "]");
-            }
-            catch (StringIndexOutOfBoundsException e)
-            {
-                throw new IllegalArgumentException ("malformed method descriptor: [" + methoddescriptor + "]");
-            }
-        }
-        
-        String [] result = new String [_result.size ()];
-        _result.copyInto (result);
-        
-        return result;
-        */
-    }
-    
-    
-    public static String signatureToMethodDescriptor (final String [] parameterTypeDescriptors, final String returnTypeDescriptor)
-    {
-        final StringBuffer result = new StringBuffer ("(");
-        
-        for (int p = 0; p < parameterTypeDescriptors.length; p++)
-        {
-            result.append (parameterTypeDescriptors [p]);
-        }
-        
-        result.append (')');
-        result.append (returnTypeDescriptor);
-        
-        return result.toString (); 
-    }
-    
-    
-    public static String typeDescriptorToUserName (final String typedescriptor)
-    {
-        return new typeDescriptorCompiler2 ().descriptorToClass (typedescriptor);
-    }
-    
-    public static String methodDescriptorToUserName (final String methoddescriptor)
-    {
-        final String [] parameterTypes = descriptorToParameterTypes (methoddescriptor);
-        
-        final StringBuffer result = new StringBuffer ("(");
-        
-        for (int p = 0; p < parameterTypes.length; p++)
-        {
-            //System.out.println ("DESCRIPTOR: [" + parameterTypes [p] + "]");
-            
-            if (p > 0) result.append (", ");
-            
-            final String typeUserName = typeDescriptorToUserName (parameterTypes [p]);
-            int lastDot = typeUserName.lastIndexOf ('.');
-            
-            if ((lastDot < 0) || ! "java.lang.".equals (typeUserName.substring (0, lastDot + 1)))
-                result.append (typeUserName);
-            else
-                result.append (typeUserName.substring (lastDot + 1));
-        }
-        
-        result.append (')');
-        return result.toString (); 
-    }
-    
-    public static String fullMethodDescriptorToUserName (final String classJavaName, String methodName, final String methoddescriptor)
-    {
-        if ("<init>".equals (methodName))
-            methodName = simpleClassName (classJavaName);
-        if ("<clinit>".equals (methodName))
-            methodName = "<static class initializer>";
-        
-        return methodName + ' ' + methodDescriptorToUserName (methoddescriptor);
-    }
-    
-    // TODO: added most recently
-    public static String fullMethodDescriptorToFullUserName (final String classJavaName, String methodName, final String methoddescriptor)
-    {
-        if ("<init>".equals (methodName))
-            methodName = simpleClassName (classJavaName);
-        if ("<clinit>".equals (methodName))
-            methodName = "<static class initializer>";
-        
-        return classJavaName + '.' + methodName + ' ' + methodDescriptorToUserName (methoddescriptor);
-    }
-    
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-    
-    private static String simpleClassName (final String classJavaName)
-    {
-        int lastDot = classJavaName.lastIndexOf ('.');
-        
-        if (lastDot < 0)
-            return classJavaName;
-        else
-            return classJavaName.substring (lastDot + 1);
-    }
-                                     
-    
-    
-    private static final class signatureCompiler
-    {
-        String signatureDescriptor (Class [] _parameterTypes, Class _returnType)
-        {
-            emit ('(');    parameterTypes (_parameterTypes); emit (')'); returnType (_returnType);
-            
-            return m_desc.toString ();
-        }
-        
-        String typeDescriptor (Class type)
-        {
-            parameterType (type);
-            
-            return m_desc.toString ();
-        }
-        
-        
-        private void parameterTypes (Class [] _parameterTypes)
-        {
-            if (_parameterTypes != null)
-            {
-                for (int p = 0; p < _parameterTypes.length; p++)
-                {
-                    parameterType (_parameterTypes [p]);
-                }
-            }
-        }
-        
-        
-        private void returnType (Class _returnType)
-        {
-            if ((_returnType == null) || (_returnType == Void.TYPE))
-                emit ('V');
-            else
-                parameterType (_returnType);
-        }
-        
-        
-        private void parameterType (Class _parameterType)
-        {
-            if (_parameterType != null)
-            {
-                if (_parameterType.isPrimitive ()) // base type:
-                {
-                    if (byte.class == _parameterType)            emit ('B');
-                    else if (char.class == _parameterType)        emit ('C');
-                    else if (double.class == _parameterType)    emit ('D');
-                    else if (float.class == _parameterType)        emit ('F');
-                    else if (int.class == _parameterType)        emit ('I');
-                    else if (long.class == _parameterType)        emit ('J');
-                    else if (short.class == _parameterType)        emit ('S');
-                    else if (boolean.class == _parameterType)    emit ('Z');
-                }
-                else if (_parameterType.isArray ()) // array type:
-                {
-                    emit ('[');    parameterType (_parameterType.getComponentType ());
-                }
-                else // object type:
-                {
-                    emit ('L');    emit (javaNameToVMName (_parameterType.getName ())); emit (';');
-                }
-            }
-        }
-        
-        
-        private void emit (String s)
-        {
-            m_desc.append (s);
-        }
-        
-        private void emit (char c)
-        {
-            m_desc.append (c);
-        }
-        
-        
-        private StringBuffer m_desc = new StringBuffer ();
-        
-    } // end of static class
-    
-    
-    
-    private static class typeDescriptorCompiler
-    {
-        /*
-        NOTE: the following would be a very simple solution to this problem
-        
-            Class.forName ('[' + descriptor).getComponentType ();
-        
-        except it only works in MS VM.
-        */
-        
-        Class descriptorToClass (String typedescriptor) throws ClassNotFoundException
-        {
-            char first = typedescriptor.charAt (0);
-            
-            if (first == '[')
-                // array type:
-                return arrayOf (typedescriptor.substring (1));
-            else if (first == 'L')
-                // object type:
-                return Class.forName (vmNameToJavaName (typedescriptor.substring (1, typedescriptor.length() - 1)));
-            else // primitive type
-            {
-                return primitive (first);
-            }
-        }
-        
-        
-        Class arrayOf (String typedescriptor) throws ClassNotFoundException
-        {
-            char first = typedescriptor.charAt (0);
-            Class component;
-            
-            if (first == '[')
-                // array type:
-                component = arrayOf (typedescriptor.substring (1));
-            else if (first == 'L')
-                // object type:
-                component =  Class.forName (vmNameToJavaName (typedescriptor.substring (1, typedescriptor.length() - 1)));
-            else // primitive type
-            {
-                component = primitive (first);
-            }
-            
-            Object array = Array.newInstance (component, 0);
-            return array.getClass ();
-        }
-        
-        
-        Class primitive (char c) throws ClassNotFoundException
-        {
-            if (c == 'B') return byte.class;
-            else if (c == 'C') return char.class;
-            else if (c == 'D') return double.class;
-            else if (c == 'F') return float.class;
-            else if (c == 'I') return int.class;
-            else if (c == 'J') return long.class;
-            else if (c == 'S') return short.class;
-            else if (c == 'Z') return boolean.class;
-            else throw new ClassNotFoundException ("unknown base type: " + c);
-        }
-        
-    } // end of static class
-
-    
-    private static class typeDescriptorCompiler2
-    {
-        String descriptorToClass (String typedescriptor)
-        {
-            //System.out.println ("typedesc1 -> " + typedescriptor);
-            
-            char first = typedescriptor.charAt (0);
-            
-            if (first == '[')
-                // array type:
-                return arrayOf (typedescriptor.substring (1));
-            else if (first == 'L')
-                // object type:
-                return vmNameToJavaName (typedescriptor.substring (1, typedescriptor.length() - 1));
-            else // primitive type
-                return primitive (first);
-        }
-        
-        
-        String arrayOf (String typedescriptor)
-        {
-            //System.out.println ("typedesc2 -> " + typedescriptor);
-            
-            char first = typedescriptor.charAt (0);
-            String component;
-            
-            if (first == '[')
-                // array type:
-                component = arrayOf (typedescriptor.substring (1));
-            else if (first == 'L')
-                // object type:
-                component = vmNameToJavaName (typedescriptor.substring (1, typedescriptor.length() - 1));
-            else // primitive type
-                component = primitive (first);
-            
-            String array = component + " []";
-            return array;
-        }
-        
-        
-        String primitive (char c)
-        {
-            switch (c)
-            {
-            case 'B': return "byte";
-            case 'C': return "char";
-            case 'D': return "double";
-            case 'F': return "float";
-            case 'I': return "int";
-            case 'J': return "long";
-            case 'S': return "short";
-            case 'Z': return "boolean";
-            default:          
-                throw new IllegalArgumentException ("unknown primitive: " + c);
-            }
-        }
-        
-    } // end of static class
-
-    
-    private static class methodDescriptorCompiler
-    {
-        methodDescriptorCompiler (String methoddescriptor)
-        {
-            m_in = new java.io.PushbackReader (new java.io.StringReader (methoddescriptor));
-        }
-        
-        String [] getResult ()
-        {
-            final String [] result = new String [m_result.size ()];
-            m_result.toArray (result);
-            
-            return result;
-        }
-        
-        void methodDescriptor () throws IOException
-        {
-            consume ('(');
-            
-            char c;
-            while ((c = (char) m_in.read ()) != ')')
-            {
-                m_in.unread (c);
-                parameterDescriptor ();
-            }
-            returnDescriptor ();
-        }
-        
-        void parameterDescriptor () throws IOException
-        {
-            fieldType ();
-            newToken ();
-        }
-        
-        void returnDescriptor () throws IOException
-        {
-            char c = (char) m_in.read ();
-            
-            switch (c)
-            {
-            case 'V':
-                m_token.append (c);
-                break;
-                
-            default:
-                m_in.unread (c);
-                fieldType ();
-                
-            }
-            // ignore return type for now: newToken ();
-        }
-        
-        void componentType () throws IOException
-        {
-            fieldType ();
-        }
-        
-        void objectType () throws IOException
-        {
-            consume ('L');
-            m_token.append ('L');
-            
-            char c;
-            while ((c = (char) m_in.read ()) != ';')
-            {
-                m_token.append (c);
-            }
-            m_token.append (';');
-        }
-        
-        void arrayType () throws IOException
-        {
-            consume ('[');
-            m_token.append ('[');
-        
-            componentType ();
-        }
-        
-        void fieldType () throws IOException
-        {
-            char c = (char) m_in.read ();
-            m_in.unread (c);
-            
-            switch (c)
-            {
-            case 'L':
-                objectType ();
-                break;
-                
-            case '[':
-                arrayType ();
-                break;
-                
-            default:
-                baseType ();
-                break;
-            }
-        }
-
-        
-        void baseType () throws IOException
-        {
-            char c = (char) m_in.read ();
-            
-            switch (c)
-            {
-            case 'B': 
-            case 'C': 
-            case 'D':
-            case 'F':
-            case 'I':
-            case 'J':
-            case 'S':
-            case 'Z':
-                m_token.append (c);
-                break;
-                
-            default:          
-                throw new IllegalArgumentException ("unknown base type: " + c);
-            }
-        }
-        
-        
-        private void consume (char expected) throws IOException
-        {
-            char c = (char) m_in.read ();
-            
-            if (c != expected)
-                throw new IllegalArgumentException ("consumed '" + c + "' while expecting '" + expected + "'");
-        }
-        
-        
-        
-        private void newToken ()
-        {
-            //System.out.println ("NEW TOKEN [" + m_token.toString () + "]");
-            
-            m_result.add (m_token.toString ());
-            m_token.setLength (0);
-        }
-    
-        final java.util.List m_result = new java.util.ArrayList ();
-        private StringBuffer m_token = new StringBuffer ();
-        private java.io.PushbackReader m_in;
-    } // end of nested class
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/lib/UDataInputStream.java b/core/java12/com/vladium/jcd/lib/UDataInputStream.java
deleted file mode 100644
index e43d9f8..0000000
--- a/core/java12/com/vladium/jcd/lib/UDataInputStream.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: UDataInputStream.java,v 1.1.1.1.2.1 2004/07/10 03:34:53 vlad_r Exp $
- */
-package com.vladium.jcd.lib;
-
-import java.io.DataInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * A trivial extension to java.io.DataInputStream to provide methods for
- * reading unsigned 16- and 32-bit integers with simple mnemonics. It uses
- * correspondingly wider native types to preserve the full range of the unsigned
- * types.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class UDataInputStream extends DataInputStream
-{
-    // public: ................................................................
-
-    
-    public UDataInputStream (final InputStream _in)
-    {
-        super (_in);
-    }
-
-    
-    public final int readU2 () throws IOException
-    {
-        final short value = readShort ();
-        
-        return ((int) value) & 0xFFFF; // widening cast sign-extends
-    }
-    
-    
-    public final long readU4 () throws IOException
-    {
-        final int value = readInt ();
-        
-        return ((long) value) & 0xFFFFFFFFL; // widening cast sign-extends
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/lib/UDataOutputStream.java b/core/java12/com/vladium/jcd/lib/UDataOutputStream.java
deleted file mode 100644
index 0fb9f0b..0000000
--- a/core/java12/com/vladium/jcd/lib/UDataOutputStream.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: UDataOutputStream.java,v 1.1.1.1.2.1 2004/07/10 03:34:53 vlad_r Exp $
- */
-package com.vladium.jcd.lib;
-
-import java.io.DataOutputStream;
-import java.io.IOException;
-import java.io.OutputStream;
-
-// ----------------------------------------------------------------------------
-/**
- * A trivial extension to java.io.DataInputStream to provide methods for
- * writing unsigned 16- and 32-bit integers with simple mnemonics. It uses
- * correspondingly wider native types to preserve the full range of the unsigned
- * types.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class UDataOutputStream extends DataOutputStream
-{
-    // public: ................................................................
-
-    
-    public UDataOutputStream (final OutputStream _out)
-    {
-        super (_out);
-    }
-    
-    
-    public final void writeU2 (final int uint) throws IOException
-    {
-        writeShort ((short) uint); // this narrowing cast is Ok
-    }
-    
-    
-    public final void writeU4 (final long ulong) throws IOException
-    {
-        writeInt ((int) ulong); // this narrowing cast is Ok
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/opcodes/IOpcodeVisitor.java b/core/java12/com/vladium/jcd/opcodes/IOpcodeVisitor.java
deleted file mode 100644
index f4fee3c..0000000
--- a/core/java12/com/vladium/jcd/opcodes/IOpcodeVisitor.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IOpcodeVisitor.java,v 1.1.1.1 2004/05/09 16:57:51 vlad_r Exp $
- */
-package com.vladium.jcd.opcodes;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IOpcodeVisitor
-{
-    // public: ................................................................
-    
-    void visit (int opcode, boolean wide, int offset, Object ctx);
-
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/jcd/opcodes/IOpcodes.java b/core/java12/com/vladium/jcd/opcodes/IOpcodes.java
deleted file mode 100644
index 2927b10..0000000
--- a/core/java12/com/vladium/jcd/opcodes/IOpcodes.java
+++ /dev/null
@@ -1,607 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IOpcodes.java,v 1.1.1.1.2.1 2004/07/10 03:34:52 vlad_r Exp $
- */
-package com.vladium.jcd.opcodes;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IOpcodes
-{
-    // public: ................................................................
-        
-    //  opcode              hex     dec opbytes stackwords wideable    
-    int _nop              = 0x00; // 00     0   0
-    int _aconst_null      = 0x01; // 01     0   +1
-    int _iconst_m1        = 0x02; // 02     0   +1
-    int _iconst_0         = 0x03; // 03     0   +1
-    int _iconst_1         = 0x04; // 04     0   +1
-    int _iconst_2         = 0x05; // 05     0   +1
-    int _iconst_3         = 0x06; // 06     0   +1
-    int _iconst_4         = 0x07; // 07     0   +1
-    int _iconst_5         = 0x08; // 08     0   +1
-    int _lconst_0         = 0x09; // 09     0   +2
-    int _lconst_1         = 0x0A; // 10     0   +2
-    int _fconst_0         = 0x0B; // 11     0   +1
-    int _fconst_1         = 0x0C; // 12     0   +1
-    int _fconst_2         = 0x0D; // 13     0   +1
-    int _dconst_0         = 0x0E; // 14     0   +2
-    int _dconst_1         = 0x0F; // 15     0   +2
-    int _bipush           = 0x10; // 16     1   +1
-    int _sipush           = 0x11; // 17     2   +1
-    int _ldc              = 0x12; // 18     1   +1
-    int _ldc_w            = 0x13; // 19     2   +1
-    int _ldc2_w           = 0x14; // 20     2   +2
-    int _iload            = 0x15; // 21     1   +1  true
-    int _lload            = 0x16; // 22     1   +2  true
-    int _fload            = 0x17; // 23     1   +1  true
-    int _dload            = 0x18; // 24     1   +2  true
-    int _aload            = 0x19; // 25     1   +1  true  
-    int _iload_0          = 0x1A; // 26     0   +1
-    int _iload_1          = 0x1B; // 27     0   +1
-    int _iload_2          = 0x1C; // 28     0   +1
-    int _iload_3          = 0x1D; // 29     0   +1
-    int _lload_0          = 0x1E; // 30     0   +2
-    int _lload_1          = 0x1F; // 31     0   +2
-    int _lload_2          = 0x20; // 32     0   +2
-    int _lload_3          = 0x21; // 33     0   +2
-    int _fload_0          = 0x22; // 34     0   +1
-    int _fload_1          = 0x23; // 35     0   +1
-    int _fload_2          = 0x24; // 36     0   +1
-    int _fload_3          = 0x25; // 37     0   +1
-    int _dload_0          = 0x26; // 38     0   +2
-    int _dload_1          = 0x27; // 39     0   +2
-    int _dload_2          = 0x28; // 40     0   +2
-    int _dload_3          = 0x29; // 41     0   +2
-    int _aload_0          = 0x2A; // 42     0   +1
-    int _aload_1          = 0x2B; // 43     0   +1
-    int _aload_2          = 0x2C; // 44     0   +1
-    int _aload_3          = 0x2D; // 45     0   +1
-    int _iaload           = 0x2E; // 46     0   -1
-    int _laload           = 0x2F; // 47     0   0
-    int _faload           = 0x30; // 48     0   -1
-    int _daload           = 0x31; // 49     0   0
-    int _aaload           = 0x32; // 50     0   -1
-    int _baload           = 0x33; // 51     0   -1
-    int _caload           = 0x34; // 52     0   -1
-    int _saload           = 0x35; // 53     0   -1
-    int _istore           = 0x36; // 54     1   -1  true
-    int _lstore           = 0x37; // 55     1   -2  true
-    int _fstore           = 0x38; // 56     1   -1  true
-    int _dstore           = 0x39; // 57     1   -2  true
-    int _astore           = 0x3A; // 58     1   -1  true
-    int _istore_0         = 0x3B; // 59     0   -1
-    int _istore_1         = 0x3C; // 60     0   -1
-    int _istore_2         = 0x3D; // 61     0   -1
-    int _istore_3         = 0x3E; // 62     0   -1
-    int _lstore_0         = 0x3F; // 63     0   -2
-    int _lstore_1         = 0x40; // 64     0   -2
-    int _lstore_2         = 0x41; // 65     0   -2
-    int _lstore_3         = 0x42; // 66     0   -2
-    int _fstore_0         = 0x43; // 67     0   -1
-    int _fstore_1         = 0x44; // 68     0   -1
-    int _fstore_2         = 0x45; // 69     0   -1
-    int _fstore_3         = 0x46; // 70     0   -1
-    int _dstore_0         = 0x47; // 71     0   -2
-    int _dstore_1         = 0x48; // 72     0   -2
-    int _dstore_2         = 0x49; // 73     0   -2
-    int _dstore_3         = 0x4A; // 74     0   -2
-    int _astore_0         = 0x4B; // 75     0   -1
-    int _astore_1         = 0x4C; // 76     0   -1
-    int _astore_2         = 0x4D; // 77     0   -1
-    int _astore_3         = 0x4E; // 78     0   -1
-    int _iastore          = 0x4F; // 79     0   -3
-    int _lastore          = 0x50; // 80     0   -4
-    int _fastore          = 0x51; // 81     0   -3
-    int _dastore          = 0x52; // 82     0   -4
-    int _aastore          = 0x53; // 83     0   -3
-    int _bastore          = 0x54; // 84     0   -3
-    int _castore          = 0x55; // 85     0   -3
-    int _sastore          = 0x56; // 86     0   -3
-    int _pop              = 0x57; // 87     0   -1
-    int _pop2             = 0x58; // 88     0   -2
-    int _dup              = 0x59; // 89     0   +1
-    int _dup_x1           = 0x5A; // 90     0   +1
-    int _dup_x2           = 0x5B; // 91     0   +1
-    int _dup2             = 0x5C; // 92     0   +2
-    int _dup2_x1          = 0x5D; // 93     0   +2
-    int _dup2_x2          = 0x5E; // 94     0   +2
-    int _swap             = 0x5F; // 95     0   0
-    int _iadd             = 0x60; // 96     0   -1
-    int _ladd             = 0x61; // 97     0   -2
-    int _fadd             = 0x62; // 98     0   -1
-    int _dadd             = 0x63; // 99     0   -2
-    int _isub             = 0x64; // 100    0   -1
-    int _lsub             = 0x65; // 101    0   -2
-    int _fsub             = 0x66; // 102    0   -1
-    int _dsub             = 0x67; // 103    0   -2
-    int _imul             = 0x68; // 104    0   -1
-    int _lmul             = 0x69; // 105    0   -2
-    int _fmul             = 0x6A; // 106    0   -1
-    int _dmul             = 0x6B; // 107    0   -2
-    int _idiv             = 0x6C; // 108    0   -1
-    int _ldiv             = 0x6D; // 109    0   -2
-    int _fdiv             = 0x6E; // 110    0   -1
-    int _ddiv             = 0x6F; // 111    0   -2
-    int _irem             = 0x70; // 112    0   -1
-    int _lrem             = 0x71; // 113    0   -2
-    int _frem             = 0x72; // 114    0   -1
-    int _drem             = 0x73; // 115    0   -2
-    int _ineg             = 0x74; // 116    0   0
-    int _lneg             = 0x75; // 117    0   0
-    int _fneg             = 0x76; // 118    0   0
-    int _dneg             = 0x77; // 119    0   0
-    int _ishl             = 0x78; // 120    0   -1
-    int _lshl             = 0x79; // 121    0   -1
-    int _ishr             = 0x7A; // 122    0   -1
-    int _lshr             = 0x7B; // 123    0   -1
-    int _iushr            = 0x7C; // 124    0   -1
-    int _lushr            = 0x7D; // 125    0   -2
-    int _iand             = 0x7E; // 126    0   -1
-    int _land             = 0x7F; // 127    0   -2
-    int _ior              = 0x80; // 128    0   -1
-    int _lor              = 0x81; // 129    0   -2
-    int _ixor             = 0x82; // 130    0   -1
-    int _lxor             = 0x83; // 131    0   -2
-    int _iinc             = 0x84; // 132    2   0   true    [widening is tricky here]
-    int _i2l              = 0x85; // 133    0   +1
-    int _i2f              = 0x86; // 134    0   0
-    int _i2d              = 0x87; // 135    0   +1
-    int _l2i              = 0x88; // 136    0   -1
-    int _l2f              = 0x89; // 137    0   -1
-    int _l2d              = 0x8A; // 138    0   0
-    int _f2i              = 0x8B; // 139    0   0
-    int _f2l              = 0x8C; // 140    0   +1
-    int _f2d              = 0x8D; // 141    0   +1
-    int _d2i              = 0x8E; // 142    0   -1
-    int _d2l              = 0x8F; // 143    0   0
-    int _d2f              = 0x90; // 144    0   -1
-    int _i2b              = 0x91; // 145    0   0
-    int _i2c              = 0x92; // 146    0   0
-    int _i2s              = 0x93; // 147    0   0
-    int _lcmp             = 0x94; // 148    0   -3
-    int _fcmpl            = 0x95; // 149    0   -1
-    int _fcmpg            = 0x96; // 150    0   -1
-    int _dcmpl            = 0x97; // 151    0   -3
-    int _dcmpg            = 0x98; // 152    0   -3
-    int _ifeq             = 0x99; // 153    2   -1
-    int _ifne             = 0x9A; // 154    2   -1
-    int _iflt             = 0x9B; // 155    2   -1
-    int _ifge             = 0x9C; // 156    2   -1
-    int _ifgt             = 0x9D; // 157    2   -1
-    int _ifle             = 0x9E; // 158    2   -1
-    int _if_icmpeq        = 0x9F; // 159    2   -2
-    int _if_icmpne        = 0xA0; // 160    2   -2
-    int _if_icmplt        = 0xA1; // 161    2   -2
-    int _if_icmpge        = 0xA2; // 162    2   -2
-    int _if_icmpgt        = 0xA3; // 163    2   -2
-    int _if_icmple        = 0xA4; // 164    2   -2
-    int _if_acmpeq        = 0xA5; // 165    2   -2
-    int _if_acmpne        = 0xA6; // 166    2   -2
-    int _goto             = 0xA7; // 167    2   0
-    int _jsr              = 0xA8; // 168    2   +1
-    int _ret              = 0xA9; // 169    1   0   true
-    int _tableswitch      = 0xAA; // 170    *   -1      [there are padding bytes and variable number of operands]
-    int _lookupswitch     = 0xAB; // 171    *   -1      [there are padding bytes and variable number of operands]
-    int _ireturn          = 0xAC; // 172    0   -1*     [current method returns]
-    int _lreturn          = 0xAD; // 173    0   -2*     [current method returns]
-    int _freturn          = 0xAE; // 174    0   -1*     [current method returns]
-    int _dreturn          = 0xAF; // 175    0   -2*     [current method returns]
-    int _areturn          = 0xB0; // 176    0   -1*     [current method returns]
-    int _return           = 0xB1; // 177    0   0*      [current method returns]
-    int _getstatic        = 0xB2; // 178    2   +1 or +2*   [after stack depends on the field type]
-    int _putstatic        = 0xB3; // 179    2   -1 or -2*   [after stack depends on the field type]
-    int _getfield         = 0xB4; // 180    2   0 or +1*    [after stack depends on the field type]
-    int _putfield         = 0xB5; // 181    2   -2 or -3*   [after stack depends on the field type]
-    int _invokevirtual    = 0xB6; // 182    2   *   *   [stack words pushed for the call are emptied]
-    int _invokespecial    = 0xB7; // 183    2   *   *   [stack words pushed for the call are emptied]
-    int _invokestatic     = 0xB8; // 184    2   *   *   [stack words pushed for the call are emptied]
-    int _invokeinterface  = 0xB9; // 185    4   *   *   [last operand is 0; stack words pushed for the call are emptied]
-    int _unused           = 0xBA; // 186    *   *   *   [for historical reasons, opcode value 186 is not used]
-    int _new              = 0xBB; // 187    2   +1
-    int _newarray         = 0xBC; // 188    1   0
-    int _anewarray        = 0xBD; // 189    2   0
-    int _arraylength      = 0xBE; // 190    0   0
-    int _athrow           = 0xBF; // 191    0   0*  *   [stack frame is emptied except for 1 obj ref]
-    int _checkcast        = 0xC0; // 192    2   0
-    int _instanceof       = 0xC1; // 193    2   0
-    int _monitorenter     = 0xC2; // 194    0   -1
-    int _monitorexit      = 0xC3; // 195    0   -1
-    int _wide             = 0xC4; // 196    *   *       [depends on instruction being modified]
-    int _multianewarray   = 0xC5; // 197    3   *       [variable number of stack operands]
-    int _ifnull           = 0xC6; // 198    2   -1
-    int _ifnonnull        = 0xC7; // 199    2   -1
-    int _goto_w           = 0xC8; // 200    4   0
-    int _jsr_w            = 0xC9; // 201    4   +1
-    // reserved opcodes:
-    int _breakpoint       = 0xCA; // 202
-    int _impdep1          = 0xFE; // 254
-    int _impdep2          = 0xFF; // 255
-
-    
-    String [] MNEMONICS =
-    {
-        "nop",              // 0x00    00
-        "aconst_null",      // 0x01    01
-        "iconst_m1",        // 0x02    02
-        "iconst_0",         // 0x03    03
-        "iconst_1",         // 0x04    04
-        "iconst_2",         // 0x05    05
-        "iconst_3",         // 0x06    06
-        "iconst_4",         // 0x07    07
-        "iconst_5",         // 0x08    08
-        "lconst_0",         // 0x09    09
-        "lconst_1",         // 0x0A    10
-        "fconst_0",         // 0x0B    11
-        "fconst_1",         // 0x0C    12
-        "fconst_2",         // 0x0D    13
-        "dconst_0",         // 0x0E    14
-        "dconst_1",         // 0x0F    15
-        "bipush",           // 0x10    16
-        "sipush",           // 0x11    17
-        "ldc",              // 0x12    18
-        "ldc_w",            // 0x13    19
-        "ldc2_w",           // 0x14    20
-        "iload",            // 0x15    21
-        "lload",            // 0x16    22
-        "fload",            // 0x17    23
-        "dload",            // 0x18    24
-        "aload",            // 0x19    25
-        "iload_0",          // 0x1A    26
-        "iload_1",          // 0x1B    27
-        "iload_2",          // 0x1C    28
-        "iload_3",          // 0x1D    29
-        "lload_0",          // 0x1E    30
-        "lload_1",          // 0x1F    31
-        "lload_2",          // 0x20    32
-        "lload_3",          // 0x21    33
-        "fload_0",          // 0x22    34
-        "fload_1",          // 0x23    35
-        "fload_2",          // 0x24    36
-        "fload_3",          // 0x25    37
-        "dload_0",          // 0x26    38
-        "dload_1",          // 0x27    39
-        "dload_2",          // 0x28    40
-        "dload_3",          // 0x29    41
-        "aload_0",          // 0x2A    42
-        "aload_1",          // 0x2B    43
-        "aload_2",          // 0x2C    44
-        "aload_3",          // 0x2D    45
-        "iaload",           // 0x2E    46
-        "laload",           // 0x2F    47
-        "faload",           // 0x30    48
-        "daload",           // 0x31    49
-        "aaload",           // 0x32    50
-        "baload",           // 0x33    51
-        "caload",           // 0x34    52
-        "saload",           // 0x35    53
-        "istore",           // 0x36    54
-        "lstore",           // 0x37    55
-        "fstore",           // 0x38    56
-        "dstore",           // 0x39    57
-        "astore",           // 0x3A    58
-        "istore_0",         // 0x3B    59
-        "istore_1",         // 0x3C    60
-        "istore_2",         // 0x3D    61
-        "istore_3",         // 0x3E    62
-        "lstore_0",         // 0x3F    63
-        "lstore_1",         // 0x40    64
-        "lstore_2",         // 0x41    65
-        "lstore_3",         // 0x42    66
-        "fstore_0",         // 0x43    67
-        "fstore_1",         // 0x44    68
-        "fstore_2",         // 0x45    69
-        "fstore_3",         // 0x46    70
-        "dstore_0",         // 0x47    71
-        "dstore_1",         // 0x48    72
-        "dstore_2",         // 0x49    73
-        "dstore_3",         // 0x4A    74
-        "astore_0",         // 0x4B    75
-        "astore_1",         // 0x4C    76
-        "astore_2",         // 0x4D    77
-        "astore_3",         // 0x4E    78
-        "iastore",          // 0x4F    79
-        "lastore",          // 0x50    80
-        "fastore",          // 0x51    81
-        "dastore",          // 0x52    82
-        "aastore",          // 0x53    83
-        "bastore",          // 0x54    84
-        "castore",          // 0x55    85
-        "sastore",          // 0x56    86
-        "pop",              // 0x57    87
-        "pop2",             // 0x58    88
-        "dup",              // 0x59    089
-        "dup_x1",           // 0x5A    090
-        "dup_x2",           // 0x5B    091
-        "dup2",             // 0x5C    092
-        "dup2_x1",          // 0x5D    093
-        "dup2_x2",          // 0x5E    094
-        "swap",             // 0x5F    095
-        "iadd",             // 0x60    096
-        "ladd",             // 0x61    097
-        "fadd",             // 0x62    098
-        "dadd",             // 0x63    099
-        "isub",             // 0x64    100
-        "lsub",             // 0x65    101
-        "fsub",             // 0x66    102
-        "dsub",             // 0x67    103
-        "imul",             // 0x68    104
-        "lmul",             // 0x69    105
-        "fmul",             // 0x6A    106
-        "dmul",             // 0x6B    107
-        "idiv",             // 0x6C    108
-        "ldiv",             // 0x6D    109
-        "fdiv",             // 0x6E    110
-        "ddiv",             // 0x6F    111
-        "irem",             // 0x70    112
-        "lrem",             // 0x71    113
-        "frem",             // 0x72    114
-        "drem",             // 0x73    115
-        "ineg",             // 0x74    116
-        "lneg",             // 0x75    117
-        "fneg",             // 0x76    118
-        "dneg",             // 0x77    119
-        "ishl",             // 0x78    120
-        "lshl",             // 0x79    121
-        "ishr",             // 0x7A    122
-        "lshr",             // 0x7B    123
-        "iushr",            // 0x7C    124
-        "lushr",            // 0x7D    125
-        "iand",             // 0x7E    126
-        "land",             // 0x7F    127
-        "ior",              // 0x80    128
-        "lor",              // 0x81    129
-        "ixor",             // 0x82    130
-        "lxor",             // 0x83    131
-        "iinc",             // 0x84    132
-        "i2l",              // 0x85    133
-        "i2f",              // 0x86    134
-        "i2d",              // 0x87    135
-        "l2i",              // 0x88    136
-        "l2f",              // 0x89    137
-        "l2d",              // 0x8A    138
-        "f2i",              // 0x8B    139
-        "f2l",              // 0x8C    140
-        "f2d",              // 0x8D    141
-        "d2i",              // 0x8E    142
-        "d2l",              // 0x8F    143
-        "d2f",              // 0x90    144
-        "i2b",              // 0x91    145
-        "i2c",              // 0x92    146
-        "i2s",              // 0x93    147
-        "lcmp",             // 0x94    148
-        "fcmpl",            // 0x95    149
-        "fcmpg",            // 0x96    150
-        "dcmpl",            // 0x97    151
-        "dcmpg",            // 0x98    152
-        "ifeq",             // 0x99    153
-        "ifne",             // 0x9A    154
-        "iflt",             // 0x9B    155
-        "ifge",             // 0x9C    156
-        "ifgt",             // 0x9D    157
-        "ifle",             // 0x9E    158
-        "if_icmpeq",        // 0x9F    159
-        "if_icmpne",        // 0xA0    160
-        "if_icmplt",        // 0xA1    161
-        "if_icmpge",        // 0xA2    162
-        "if_icmpgt",        // 0xA3    163
-        "if_icmple",        // 0xA4    164
-        "if_acmpeq",        // 0xA5    165
-        "if_acmpne",        // 0xA6    166
-        "goto",             // 0xA7    167
-        "jsr",              // 0xA8    168
-        "ret",              // 0xA9    169
-        "tableswitch",      // 0xAA    170
-        "lookupswitch",     // 0xAB    171
-        "ireturn",          // 0xAC    172
-        "lreturn",          // 0xAD    173
-        "freturn",          // 0xAE    174
-        "dreturn",          // 0xAF    175
-        "areturn",          // 0xB0    176
-        "return",           // 0xB1    177
-        "getstatic",        // 0xB2    178
-        "putstatic",        // 0xB3    179
-        "getfield",         // 0xB4    180
-        "putfield",         // 0xB5    181
-        "invokevirtual",    // 0xB6    182
-        "invokespecial",    // 0xB7    183
-        "invokestatic",     // 0xB8    184
-        "invokeinterface",  // 0xB9    185
-        "unused",           // 0xBA    186
-        "new",              // 0xBB    187
-        "newarray",         // 0xBC    188
-        "anewarray",        // 0xBD    189
-        "arraylength",      // 0xBE    190
-        "athrow",           // 0xBF    191
-        "checkcast",        // 0xC0    192
-        "instanceof",       // 0xC1    193
-        "monitorenter",     // 0xC2    194
-        "monitorexit",      // 0xC3    195
-        "[wide]",           // 0xC4    196
-        "multianewarray",   // 0xC5    197
-        "ifnull",           // 0xC6    198
-        "ifnonnull",        // 0xC7    199
-        "goto_w",           // 0xC8    200
-        "jsr_w"             // 0xC9    201
-    };
-    
-    
-    boolean [] CONDITIONAL_BRANCHES = clinit._CONDITIONAL_BRANCHES;
-    boolean [] COMPOUND_CONDITIONAL_BRANCHES = clinit._COMPOUND_CONDITIONAL_BRANCHES;
-    boolean [] UNCONDITIONAL_BRANCHES = clinit._UNCONDITIONAL_BRANCHES;
-    boolean [] BRANCHES = clinit._BRANCHES;
-    
-    int [] NARROW_SIZE = clinit._NARROW_SIZE; // including the opcode itself
-    int [] WIDE_SIZE = clinit._WIDE_SIZE; // including the opcode itself
-    
-    
-    static final class clinit
-    {
-        static final boolean [] _CONDITIONAL_BRANCHES;
-        static final boolean [] _COMPOUND_CONDITIONAL_BRANCHES;
-        static final boolean [] _UNCONDITIONAL_BRANCHES;
-        static final boolean [] _BRANCHES;
-        static final int [] _NARROW_SIZE;
-        static final int [] _WIDE_SIZE;
-        
-        static
-        {
-            final int opcodeCount = MNEMONICS.length;
-            
-            _CONDITIONAL_BRANCHES = new boolean [opcodeCount];
-            
-            _CONDITIONAL_BRANCHES [_ifeq] = true;
-            _CONDITIONAL_BRANCHES [_iflt] = true;
-            _CONDITIONAL_BRANCHES [_ifle] = true;
-            _CONDITIONAL_BRANCHES [_ifne] = true;
-            _CONDITIONAL_BRANCHES [_ifgt] = true;
-            _CONDITIONAL_BRANCHES [_ifge] = true;
-            _CONDITIONAL_BRANCHES [_ifnull] = true;
-            _CONDITIONAL_BRANCHES [_ifnonnull] = true;
-            _CONDITIONAL_BRANCHES [_if_icmpeq] = true;
-            _CONDITIONAL_BRANCHES [_if_icmpne] = true;
-            _CONDITIONAL_BRANCHES [_if_icmplt] = true;
-            _CONDITIONAL_BRANCHES [_if_icmpgt] = true;
-            _CONDITIONAL_BRANCHES [_if_icmple] = true;
-            _CONDITIONAL_BRANCHES [_if_icmpge] = true;
-            _CONDITIONAL_BRANCHES [_if_acmpeq] = true;
-            _CONDITIONAL_BRANCHES [_if_acmpne] = true;
-
-
-            _COMPOUND_CONDITIONAL_BRANCHES = new boolean [opcodeCount];
-            
-            _COMPOUND_CONDITIONAL_BRANCHES [_tableswitch] = true;
-            _COMPOUND_CONDITIONAL_BRANCHES [_lookupswitch] = true;
-
-            
-            _UNCONDITIONAL_BRANCHES = new boolean  [opcodeCount];
-            
-            _UNCONDITIONAL_BRANCHES [_goto] = true;
-            _UNCONDITIONAL_BRANCHES [_goto_w] = true;
-            _UNCONDITIONAL_BRANCHES [_jsr] = true;
-            _UNCONDITIONAL_BRANCHES [_jsr_w] = true;
-            _UNCONDITIONAL_BRANCHES [_ret] = true;
-
-            _UNCONDITIONAL_BRANCHES [_ireturn] = true;
-            _UNCONDITIONAL_BRANCHES [_lreturn] = true;
-            _UNCONDITIONAL_BRANCHES [_freturn] = true;
-            _UNCONDITIONAL_BRANCHES [_dreturn] = true;
-            _UNCONDITIONAL_BRANCHES [_areturn] = true;
-            _UNCONDITIONAL_BRANCHES [_return] = true;
-
-            _UNCONDITIONAL_BRANCHES [_athrow] = true;
-
-
-            _BRANCHES = new boolean [opcodeCount];
-            
-            for (int o = 0; o < opcodeCount; ++ o)
-                if (_CONDITIONAL_BRANCHES [o]) _BRANCHES [o] = true;
-
-            for (int o = 0; o < opcodeCount; ++ o)
-                if (_COMPOUND_CONDITIONAL_BRANCHES [o]) _BRANCHES [o] = true;
-
-            for (int o = 0; o < opcodeCount; ++ o)
-                if (_UNCONDITIONAL_BRANCHES [o]) _BRANCHES [o] = true;
-
-
-            _NARROW_SIZE = new int [opcodeCount];
-            
-            for (int o = 0; o < opcodeCount; ++ o) _NARROW_SIZE [o] = 1;
-            
-            _NARROW_SIZE [_bipush] = 2;
-            _NARROW_SIZE [_sipush] = 3;
-
-            _NARROW_SIZE [_ldc] = 2;
-            _NARROW_SIZE [_ldc_w] = 3;
-            _NARROW_SIZE [_ldc2_w] = 3;
-
-            _NARROW_SIZE [_iload] = 2;
-            _NARROW_SIZE [_lload] = 2;
-            _NARROW_SIZE [_fload] = 2;
-            _NARROW_SIZE [_dload] = 2;
-            _NARROW_SIZE [_aload] = 2;
-            _NARROW_SIZE [_istore] = 2;
-            _NARROW_SIZE [_lstore] = 2;
-            _NARROW_SIZE [_fstore] = 2;
-            _NARROW_SIZE [_dstore] = 2;
-            _NARROW_SIZE [_astore] = 2;
-
-            _NARROW_SIZE [_iinc] = 3;
-
-            _NARROW_SIZE [_ifeq] = 3;
-            _NARROW_SIZE [_ifne] = 3;
-            _NARROW_SIZE [_iflt] = 3;
-            _NARROW_SIZE [_ifge] = 3;
-            _NARROW_SIZE [_ifgt] = 3;
-            _NARROW_SIZE [_ifle] = 3;
-            _NARROW_SIZE [_if_icmpeq] = 3;
-            _NARROW_SIZE [_if_icmpne] = 3;
-            _NARROW_SIZE [_if_icmplt] = 3;
-            _NARROW_SIZE [_if_icmpge] = 3;
-            _NARROW_SIZE [_if_icmpgt] = 3;
-            _NARROW_SIZE [_if_icmple] = 3;
-            _NARROW_SIZE [_if_acmpeq] = 3;
-            _NARROW_SIZE [_if_acmpne] = 3;
-            _NARROW_SIZE [_goto] = 3;
-            _NARROW_SIZE [_jsr] = 3;
-            _NARROW_SIZE [_ifnull] = 3;
-            _NARROW_SIZE [_ifnonnull] = 3;
-
-            _NARROW_SIZE [_ret] = 2;
-
-            _NARROW_SIZE [_lookupswitch] = -1;   // special case #2
-            _NARROW_SIZE [_tableswitch] = 0;    // special case #1
-            
-            _NARROW_SIZE [_getstatic] = 3;
-            _NARROW_SIZE [_putstatic] = 3;
-            _NARROW_SIZE [_getfield] = 3;
-            _NARROW_SIZE [_putfield] = 3;
-
-            _NARROW_SIZE [_invokevirtual] = 3;
-            _NARROW_SIZE [_invokespecial] = 3;
-            _NARROW_SIZE [_invokestatic] = 3;
-
-            _NARROW_SIZE [_invokeinterface] = 5;
-                
-            _NARROW_SIZE [_new] = 3;
-            _NARROW_SIZE [_checkcast] = 3;
-            _NARROW_SIZE [_instanceof] = 3;
-
-            _NARROW_SIZE [_newarray] = 2;
-            _NARROW_SIZE [_anewarray] = 3;
-            _NARROW_SIZE [_multianewarray] = 4;
-
-            _NARROW_SIZE [_goto_w] = 5;
-            _NARROW_SIZE [_jsr_w] = 5;
-            
-            
-            _WIDE_SIZE = (int []) _NARROW_SIZE.clone ();
-            
-            _WIDE_SIZE [_iload] = 3;
-            _WIDE_SIZE [_lload] = 3;
-            _WIDE_SIZE [_fload] = 3;
-            _WIDE_SIZE [_dload] = 3;
-            _WIDE_SIZE [_aload] = 3;
-            _WIDE_SIZE [_istore] = 3;
-            _WIDE_SIZE [_lstore] = 3;
-            _WIDE_SIZE [_fstore] = 3;
-            _WIDE_SIZE [_dstore] = 3;
-            _WIDE_SIZE [_astore] = 3;
-            
-            _WIDE_SIZE [_iinc] = 5;
-            
-            _WIDE_SIZE [_ret] = 3;
-        }
-        
-    } // end of nested class
-    
-} // end of interface
-// ----------------------------------------------------------------------------
-
diff --git a/core/java12/com/vladium/jcd/parser/ClassDefParser.java b/core/java12/com/vladium/jcd/parser/ClassDefParser.java
deleted file mode 100644
index 8a9fb24..0000000
--- a/core/java12/com/vladium/jcd/parser/ClassDefParser.java
+++ /dev/null
@@ -1,311 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ClassDefParser.java,v 1.1.1.1 2004/05/09 16:57:51 vlad_r Exp $
- */
-package com.vladium.jcd.parser;
-
-import java.io.InputStream;
-import java.io.IOException;
-
-import com.vladium.jcd.cls.*;
-import com.vladium.jcd.cls.attribute.*;
-import com.vladium.jcd.cls.constant.*;
-import com.vladium.jcd.lib.UDataInputStream;
-import com.vladium.util.ByteArrayIStream;
-
-// ----------------------------------------------------------------------------
-/**
- * This class provides an API for parsing a stream or array of bytecodes into a
- * {@link ClassDef} AST.
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-abstract class ClassDefParser
-{
-    // public: ................................................................
-
-    
-    /**
-     * Parses an array of bytecodes into a {@link ClassDef}.
-     */
-    public static ClassDef parseClass (final byte [] bytes)
-        throws IOException
-    {
-        if (bytes == null) throw new IllegalArgumentException ("null input: bytes");
-        
-        classParser parser = new classParser (new UDataInputStream (new ByteArrayIStream (bytes)));
-        
-        return parser.class_table ();
-    }
-    
-    /**
-     * Parses an array of bytecodes into a {@link ClassDef}.
-     */
-    public static ClassDef parseClass (final byte [] bytes, final int length)
-        throws IOException
-    {
-        if (bytes == null) throw new IllegalArgumentException ("null input: bytes");
-        
-        classParser parser = new classParser (new UDataInputStream (new ByteArrayIStream (bytes, length)));
-        
-        return parser.class_table ();
-    }
-    
-    
-    /**
-     * Parses a stream of bytecodes into a {@link ClassDef}.
-     */
-    public static ClassDef parseClass (final InputStream bytes)
-        throws IOException
-    {
-        if (bytes == null) throw new IllegalArgumentException ("null input: bytes");
-        
-        classParser parser = new classParser (new UDataInputStream (bytes));
-        
-        return parser.class_table ();
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-
-    static final boolean PARSE_SERIAL_VERSION_UID = true;    
-    
-    static final String SERIAL_VERSION_UID_FIELD_NAME   = "serialVersionUID";
-    static final int SERIAL_VERSION_UID_FIELD_MASK      = IAccessFlags.ACC_STATIC | IAccessFlags.ACC_FINAL;
-
-    // private: ...............................................................
-
-    
-    /**
-     * All the parsing work is done by this class and its class_table method. The
-     * work that needs to be done is not complicated, but is rather monotonous -- see
-     * Chapter 4 of VM spec 1.0 for the class file format.
-     */
-    private static final class classParser
-    {
-        classParser (final UDataInputStream bytes)
-        {
-            m_bytes = bytes;
-        }
-
-        
-        ClassDef class_table () throws IOException
-        {
-            m_table = new ClassDef ();
-            
-            
-            magic ();
-            version ();
-            
-            if (DEBUG) System.out.println (s_line);
-            
-            constant_pool ();
-            
-            if (DEBUG) System.out.println (s_line);
-            
-            access_flags ();
-            this_class ();
-            super_class ();
-            
-            if (DEBUG) System.out.println (s_line);
-            
-            interfaces ();
-            if (DEBUG) System.out.println (s_line);
-            
-            fields ();
-            if (DEBUG) System.out.println (s_line);
-            
-            methods ();
-            if (DEBUG) System.out.println (s_line);
-            
-            attributes ();
-            if (DEBUG) System.out.println (s_line);
-            
-            return m_table;
-        }
-        
-        
-        void magic () throws IOException
-        {
-            final long magic = m_bytes.readU4 ();
-            if (DEBUG) System.out.println ("magic: [" + Long.toHexString (magic) + ']');
-            
-            m_table.setMagic (magic);
-        }
-        
-        
-        void version () throws IOException
-        {
-            final int minor_version = m_bytes.readU2 ();
-            final int major_version = m_bytes.readU2 ();
-            
-            if (DEBUG)
-            {
-                System.out.println ("major_version: [" + major_version + ']');
-                System.out.println ("minor_version: [" + minor_version + ']');
-            }
-            
-            m_table.setVersion (new int [] {major_version, minor_version});
-        }
-        
-        
-        void constant_pool () throws IOException
-        {
-            final int constant_pool_count = m_bytes.readU2 ();
-            if (DEBUG) System.out.println ("constant_pool_count = " + constant_pool_count + " [actual number of entries = " + (constant_pool_count - 1) + "]");
-            
-            final IConstantCollection constants = m_table.getConstants();
-            
-            for (int index = 1; index < constant_pool_count; ++ index)
-            {
-                final CONSTANT_info cp_info = CONSTANT_info.new_CONSTANT_info (m_bytes);
-                constants.add (cp_info);
-                
-                if (DEBUG) System.out.println ("[" + index + "] constant: " + cp_info);
-                
-                if ((cp_info instanceof CONSTANT_Long_info) || (cp_info instanceof CONSTANT_Double_info))
-                    index++;
-            }
-        }
-        
-        
-        void access_flags () throws IOException
-        {
-            final int _access_flags = m_bytes.readU2 ();
-            
-            m_table.setAccessFlags (_access_flags);
-        }
-        
-        
-        void this_class () throws IOException
-        {
-            final int _class_index = m_bytes.readU2 ();
-            if (DEBUG) System.out.println ("this_class: [" + _class_index + ']');
-            
-            m_table.setThisClassIndex (_class_index);
-        }
-        
-        
-        void super_class () throws IOException
-        {
-            final int _class_index = m_bytes.readU2 ();
-            if (DEBUG) System.out.println ("super_class: [" + _class_index + ']');
-            
-            m_table.setSuperClassIndex (_class_index);
-        }
-        
-        
-        void interfaces () throws IOException
-        {
-            final int _interfaces_count = m_bytes.readU2 ();
-            if (DEBUG) System.out.println ("interfaces_count = " + _interfaces_count);
-            
-            for (int i = 0; i < _interfaces_count; i++)
-            {
-                int _interface_index = m_bytes.readU2 ();
-                if (DEBUG) System.out.println ("[" + i + "] interface: " + _interface_index);
-                
-                m_table.getInterfaces().add (_interface_index);
-            }
-        }
-        
-        
-        void fields () throws IOException
-        {
-            final int _fields_count = m_bytes.readU2 ();
-            if (DEBUG) System.out.println ("fields_count = " + _fields_count);
-            
-            final IConstantCollection constantPool = m_table.getConstants ();
-            
-            for (int i = 0; i < _fields_count; i++)
-            {
-                final Field_info field_info = new Field_info (constantPool, m_bytes);
-                if (DEBUG)
-                {
-                    System.out.println ("[" + i + "] field: " + field_info);
-                    System.out.println ();
-                }
-                
-                m_table.getFields().add (field_info);
-                
-                if (PARSE_SERIAL_VERSION_UID)
-                
-                if (((field_info.getAccessFlags () & SERIAL_VERSION_UID_FIELD_MASK) == SERIAL_VERSION_UID_FIELD_MASK)
-                    && SERIAL_VERSION_UID_FIELD_NAME.equals (field_info.getName (m_table)))
-                {
-                    final IAttributeCollection attributes = field_info.getAttributes ();
-                    for (int a = 0, aLimit = attributes.size (); a < aLimit; ++ a)
-                    {
-                        final Attribute_info attr_info = attributes.get (a);
-                        
-                        if (attr_info instanceof ConstantValueAttribute_info)
-                        {
-                            final CONSTANT_literal_info constant_value = ((ConstantValueAttribute_info) attr_info).getValue (m_table);
-                            if (constant_value instanceof CONSTANT_Long_info)
-                                m_table.setDeclaredSUID (((CONSTANT_Long_info) constant_value).m_value);
-                        }
-                    }
-                }
-            }
-        }
-        
-        
-        void methods () throws IOException
-        {
-            final int _methods_count = m_bytes.readU2 ();
-            if (DEBUG) System.out.println ("methods_count = " + _methods_count);
-            
-            final IConstantCollection constantPool = m_table.getConstants ();
-            
-            for (int i = 0; i < _methods_count; i++)
-            {
-                final Method_info method_info = new Method_info (constantPool, m_bytes);
-                if (DEBUG)
-                {
-                    System.out.println ("[" + i + "] method: " + method_info);
-                    System.out.println ();
-                }
-                
-                m_table.getMethods().add (method_info);
-            }
-        }
-        
-        
-        void attributes () throws IOException
-        {
-            final int _attributes_count = m_bytes.readU2 ();
-            if (DEBUG) System.out.println ("attributes_count = " + _attributes_count);
-            
-            IConstantCollection constantPool = m_table.getConstants ();
-            
-            for (int i = 0; i < _attributes_count; i++)
-            {
-                Attribute_info attribute_info = Attribute_info.new_Attribute_info (constantPool, m_bytes);
-                if (DEBUG)
-                {
-                    System.out.println ("[" + i + "] attribute: " + attribute_info);
-                    System.out.println ();
-                }
-                
-                m_table.getAttributes().add (attribute_info);
-            }
-        }
-        
-        
-        private final UDataInputStream m_bytes;
-        private ClassDef m_table;
-    
-        private static final boolean DEBUG = false;
-        private static final String s_line = "------------------------------------------------------------------------";
-
-    } // end of static class    
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/logging/ILogLevels.java b/core/java12/com/vladium/logging/ILogLevels.java
deleted file mode 100644
index 33a52b5..0000000
--- a/core/java12/com/vladium/logging/ILogLevels.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ILogLevels.java,v 1.1.1.1.2.1 2004/07/16 23:32:29 vlad_r Exp $
- */
-package com.vladium.logging;
-
-// ----------------------------------------------------------------------------
-/**
- * An enumeration of log level values used in conjunction with the API in
- * {@link Logger} 
- * 
- * @see Logger
- * 
- * @author Vlad Roubtsov, (C) 2001
- */
-public
-interface ILogLevels
-{
-    // public: ................................................................
-    
-    // note: must start with 0
-    
-    /** log level excluding all but severe errors */
-    int SEVERE          = 0;    // "-silent"
-    /** log level for quieter than normal operation */
-    int WARNING         = 1;    // "-quiet"
-    /** default log level */
-    int INFO            = 2;    // default
-    /** log level for chattier than normal operation */
-    int VERBOSE         = 3;    // "-verbose"
-    
-    // debug levels:
-    
-    /** debug trace log level */
-    int TRACE1          = 4;
-    /** finer debug trace log level */
-    int TRACE2          = 5;
-    /** finest debug trace log level */
-    int TRACE3          = 6;
-    
-    // special constants:
-    
-    /** setting log level to NONE disables all logging */
-    int NONE            = -1;
-    /** setting log level to ALL enables all log levels */
-    int ALL             = TRACE3 + 1;
-    
-
-    // human readable strings: 
-    
-    String SEVERE_STRING    = "severe";
-    String SILENT_STRING    = "silent";
-    String WARNING_STRING   = "warning";
-    String QUIET_STRING     = "quiet";
-    String INFO_STRING      = "info";
-    String VERBOSE_STRING   = "verbose";
-    String TRACE1_STRING    = "trace1";
-    String TRACE2_STRING    = "trace2";
-    String TRACE3_STRING    = "trace3";
-    
-    String NONE_STRING      = "none";
-    String ALL_STRING       = "all";
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/logging/Logger.java b/core/java12/com/vladium/logging/Logger.java
deleted file mode 100644
index 0e69a08..0000000
--- a/core/java12/com/vladium/logging/Logger.java
+++ /dev/null
@@ -1,611 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Logger.java,v 1.1.1.1.2.2 2004/07/16 23:32:29 vlad_r Exp $
- */
-package com.vladium.logging;
-
-import java.io.PrintWriter;
-import java.io.StringWriter;
-import java.util.HashSet;
-import java.util.LinkedList;
-import java.util.NoSuchElementException;
-import java.util.Properties;
-import java.util.Set;
-import java.util.StringTokenizer;
-
-import com.vladium.emma.AppLoggers;
-import com.vladium.emma.IAppConstants;
-import com.vladium.util.ClassLoaderResolver;
-import com.vladium.util.Property;
-import com.vladium.util.Strings;
-
-// ----------------------------------------------------------------------------
-/**
- * A simple Java version-independent logging framework. Each Logger is also
- * an immutable context that encapsulates configuration elements like the
- * logging verbosity level etc. In general, a Logger is looked up as an
- * inheritable thread-local piece of data. This decouples classes and
- * logging configurations in a way that seems difficult with log4j.<P>
- * 
- * Note that a given class is free to cache its context in an instance field
- * if the class is instantiated and used only on a single thread (or a set of
- * threads that are guaranteed to share the same logging context). [This is
- * different from the usual log4j pattern of caching a logger in a class static
- * field]. In other cases (e.g., the instrumentation runtime), it makes more
- * sense to scope a context to a single method invocation.<P>
- * 
- * Every log message is structured as follows:
- * <OL>
- *  <LI> message is prefixed with the prefix string set in the Logger if that is
- * not null;
- *  <LI> if the calling class could be identified and it supplied the calling
- * method name, the calling method is identified with all name components that
- * are not null;
- *  <LI> caller-supplied message is logged, if not null;
- *  <LI> caller-supplied Throwable is dumped starting with a new line, if not null.
- * </OL>
- * 
- * MT-safety: a given Logger instance will not get corrupted by concurrent
- * usage from multiple threads and guarantees that data written to the underlying
- * PrintWriter in a single log call will be done in one atomic print() step.
- * 
- * @see ILogLevels
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class Logger implements ILogLevels
-{
-    // public: ................................................................
-    
-    // TODO: update javadoc for 'logCaller'
-    // TODO: need isLoggable (Class)
-    
-    public static Logger create (final int level, final PrintWriter out, final String prefix, final Set classMask)
-    {
-        if ((level < NONE) || (level > ALL))
-            throw new IllegalArgumentException ("invalid log level: " + level);
-        
-        if ((out == null) || out.checkError ())
-            throw new IllegalArgumentException ("null or corrupt input: out");
-        
-        return new Logger (level, out, prefix, classMask);
-    }
-    
-    /**
-     * This works as a cloning creator of sorts.
-     * 
-     * @param level
-     * @param out
-     * @param prefix
-     * @param classMask
-     * @param base
-     * @return
-     */
-    public static Logger create (final int level, final PrintWriter out, final String prefix, final Set classMask,
-                                 final Logger base)
-    {
-        if (base == null)
-        {
-            return create (level, out, prefix, classMask);
-        }
-        else
-        {
-            final int _level = level >= NONE
-                ? level
-                : base.m_level;
-                
-            final PrintWriter _out = (out != null) && ! out.checkError ()
-                ? out
-                : base.m_out;
-            
-            // TODO: do a better job of logger cloning
-            final String _prefix = prefix;
-//            final String _prefix = prefix != null
-//                ? prefix
-//                : base.m_prefix;
-            
-            final Set _classMask = classMask != null
-                ? classMask
-                : base.m_classMask;
-        
-        
-            return new Logger (_level, _out, _prefix, _classMask);
-        }
-    }
-  
-
-    /**
-     * A quick method to determine if logging is enabled at a given level.
-     * This method acquires no monitors and should be used when calling one of
-     * log() or convenience logging methods directly incurs significant
-     * parameter construction overhead.
-     * 
-     * @see ILogLevels
-     */
-    public final boolean isLoggable (final int level)
-    {
-        return (level <= m_level);
-    }
-
-    /**
-     * A convenience method equivalent to isLoggable(INFO).
-     */
-    public final boolean atINFO ()
-    {
-        return (INFO <= m_level);
-    }
-    
-    /**
-     * A convenience method equivalent to isLoggable(VERBOSE).
-     */
-    public final boolean atVERBOSE ()
-    {
-        return (VERBOSE <= m_level);
-    }
-    
-    /**
-     * A convenience method equivalent to isLoggable(TRACE1).
-     */
-    public final boolean atTRACE1 ()
-    {
-        return (TRACE1 <= m_level);
-    }
-
-    /**
-     * A convenience method equivalent to isLoggable(TRACE2).
-     */
-    public final boolean atTRACE2 ()
-    {
-        return (TRACE2 <= m_level);
-    }
-
-    /**
-     * A convenience method equivalent to isLoggable(TRACE3).
-     */
-    public final boolean atTRACE3 ()
-    {
-        return (TRACE3 <= m_level);
-    }
-
-
-    /**
-     * A convenience method to log 'msg' from an anonymous calling method
-     * at WARNING level.
-     * 
-     * @param msg log message [ignored if null]
-     */
-    public final void warning (final String msg)
-    {
-        _log (WARNING, null, msg, false);
-    }
-    
-    /**
-     * A convenience method to log 'msg' from an anonymous calling method
-     * at INFO level.
-     * 
-     * @param msg log message [ignored if null]
-     */
-    public final void info (final String msg)
-    {
-        _log (INFO, null, msg, false);
-    }
-    
-    /**
-     * A convenience method to log 'msg' from an anonymous calling method
-     * at VERBOSE level.
-     * 
-     * @param msg log message [ignored if null]
-     */
-    public final void verbose (final String msg)
-    {
-        _log (VERBOSE, null, msg, false);
-    }
-
-    
-    /**
-     * A convenience method equivalent to log(TRACE1, method, msg).
-     * 
-     * @param method calling method name [ignored if null]
-     * @param msg log message [ignored if null]
-     */
-    public final void trace1 (final String method, final String msg)
-    {
-        _log (TRACE1, method, msg, true);
-    }
-    
-    /**
-     * A convenience method equivalent to log(TRACE2, method, msg).
-     * 
-     * @param method calling method name [ignored if null]
-     * @param msg log message [ignored if null]
-     */
-    public final void trace2 (final String method, final String msg)
-    {
-        _log (TRACE2, method, msg, true);
-    }
-    
-    /**
-     * A convenience method equivalent to log(TRACE3, method, msg).
-     * 
-     * @param method calling method name [ignored if null]
-     * @param msg log message [ignored if null]
-     */
-    public final void trace3 (final String method, final String msg)
-    {
-        _log (TRACE3, method, msg, true);
-    }
-
-    /**
-     * Logs 'msg' from an unnamed calling method.
-     * 
-     * @param level level to log at [the method does nothing if this is less
-     * than the set level].
-     * @param msg log message [ignored if null]
-     */        
-    public final void log (final int level, final String msg, final boolean logCaller)
-    {
-        _log (level, null, msg, logCaller);
-    }
-    
-    /**
-     * Logs 'msg' from a given calling method.
-     * 
-     * @param level level to log at [the method does nothing if this is less
-     * than the set level].
-     * @param method calling method name [ignored if null]
-     * @param msg log message [ignored if null]
-     */        
-    public final void log (final int level, final String method, final String msg, final boolean logCaller)
-    {
-        _log (level, method, msg, logCaller);
-    }
-
-    /**
-     * Logs 'msg' from an unnamed calling method followed by the 'throwable' stack
-     * trace dump.
-     *  
-     * @param level level to log at [the method does nothing if this is less
-     * than the set level].
-     * @param msg log message [ignored if null]
-     * @param throwable to dump after message [ignored if null]
-     */
-    public final void log (final int level, final String msg, final Throwable throwable)
-    {
-        _log (level, null, msg, throwable);
-    }
-    
-    /**
-     * Logs 'msg' from a given calling method followed by the 'throwable' stack
-     * trace dump.
-     *  
-     * @param level level to log at [the method does nothing if this is less
-     * than the set level].
-     * @param method calling method name [ignored if null]
-     * @param msg log message [ignored if null]
-     * @param throwable to dump after message [ignored if null]
-     */
-    public final void log (final int level, final String method, final String msg, final Throwable throwable)
-    {
-        _log (level, method, msg, throwable);
-    }
-
-    
-    /**
-     * Provides direct access to the PrintWriter used by this Logger. 
-     * 
-     * @return print writer used by this logger [never null]
-     */
-    public PrintWriter getWriter ()
-    {
-        return m_out;
-    }
-
-    
-    /**
-     * Returns the current top of the thread-local logger stack or the static
-     * Logger instance scoped to Logger.class if the stack is empty.
-     * 
-     * @return current logger [never null]
-     */
-    public static Logger getLogger ()
-    {
-        final LinkedList stack = (LinkedList) THREAD_LOCAL_STACK.get ();
-        
-        // [assertion: stack != null]
-
-        if (stack.isEmpty ())
-        {
-            return STATIC_LOGGER;
-        }
-        else
-        {
-            return (Logger) stack.getLast ();
-        }
-    }
-    
-    /**
-     * 
-     * @param ctx [may not be null]
-     */
-    public static void push (final Logger ctx)
-    {
-        if (ctx == null)
-            throw new IllegalArgumentException ("null input: ctx");
-        
-        final LinkedList stack = (LinkedList) THREAD_LOCAL_STACK.get ();
-        stack.addLast (ctx);
-    }
-    
-    /**
-     * Requiring a context parameter here helps enforce correct push/pop
-     * nesting in the caller code.
-     * 
-     * @param ctx [may not be null]
-     */
-    public static void pop (final Logger ctx)
-    {
-        // TODO: add guards for making sure only the pushing thread is allowed to
-        // execute this
-        
-        final LinkedList stack = (LinkedList) THREAD_LOCAL_STACK.get ();
-
-        try
-        {
-            final Logger current = (Logger) stack.getLast ();
-            if (current != ctx)
-                throw new IllegalStateException ("invalid context being popped: " + ctx);
-            
-            stack.removeLast ();
-            current.cleanup ();
-        }
-        catch (NoSuchElementException nsee)
-        {
-            throw new IllegalStateException ("empty logger context stack on thread [" + Thread.currentThread () + "]: " + nsee);
-        }
-    }
-
-    
-    public static int stringToLevel (final String level)
-    {
-        if (ILogLevels.SEVERE_STRING.equalsIgnoreCase (level) || ILogLevels.SILENT_STRING.equalsIgnoreCase (level))
-            return ILogLevels.SEVERE;
-        else if (ILogLevels.WARNING_STRING.equalsIgnoreCase (level) || ILogLevels.QUIET_STRING.equalsIgnoreCase (level))
-            return ILogLevels.WARNING;
-        else if (ILogLevels.INFO_STRING.equalsIgnoreCase (level))
-            return ILogLevels.INFO;
-        else if (ILogLevels.VERBOSE_STRING.equalsIgnoreCase (level))
-            return ILogLevels.VERBOSE;
-        else if (ILogLevels.TRACE1_STRING.equalsIgnoreCase (level))
-            return ILogLevels.TRACE1;
-        else if (ILogLevels.TRACE2_STRING.equalsIgnoreCase (level))
-            return ILogLevels.TRACE2;
-        else if (ILogLevels.TRACE3_STRING.equalsIgnoreCase (level))
-            return ILogLevels.TRACE3;
-        else if (ILogLevels.NONE_STRING.equalsIgnoreCase (level))
-            return ILogLevels.NONE;
-        else if (ILogLevels.ALL_STRING.equalsIgnoreCase (level))
-            return ILogLevels.ALL;
-        else
-        {
-            int _level = Integer.MIN_VALUE;
-            try
-            {
-                _level = Integer.parseInt (level);
-            }
-            catch (Exception ignore) {}
-            
-            if ((_level >= ILogLevels.NONE) && (_level <= ILogLevels.ALL))
-                return _level;
-            else
-                return ILogLevels.INFO; // default to something middle of the ground
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final class ThreadLocalStack extends InheritableThreadLocal
-    {
-        protected Object initialValue ()
-        {
-            return new LinkedList ();
-        }
-        
-    } // end of nested class
-
-    
-    private Logger (final int level, final PrintWriter out, final String prefix, final Set classMask)
-    {
-        m_level = level;
-        m_out = out;
-        m_prefix = prefix;
-        m_classMask = classMask; // no defensive clone
-    }
-
-    private void cleanup ()
-    {
-        m_out.flush ();
-    }
-    
-    private void _log (final int level, final String method,
-                       final String msg, final boolean logCaller)
-    {
-        if ((level <= m_level) && (level >= SEVERE))
-        {
-            final Class caller = logCaller ? ClassLoaderResolver.getCallerClass (2) : null;
-            final StringBuffer buf = new StringBuffer (m_prefix != null ? m_prefix + ": " : "");
-
-            if ((caller != null) || (method != null))
-            {
-                buf.append ("[");
-                
-                if (caller != null) // if the caller could not be determined, s_classMask is ignored
-                {
-                    String callerName = caller.getName ();
-                    
-                    if (callerName.startsWith (PREFIX_TO_STRIP))
-                        callerName = callerName.substring (PREFIX_TO_STRIP_LENGTH);
-                        
-                    String parentName = callerName;
-                    
-                    final int firstDollar = callerName.indexOf ('$');
-                    if (firstDollar > 0) parentName = callerName.substring (0, firstDollar);
-                    
-                    if ((m_classMask == null) || m_classMask.contains (parentName))
-                        buf.append (callerName);
-                    else
-                        return;
-                }
-                
-                if (method != null)
-                {
-                    buf.append ("::");
-                    buf.append (method);
-                }
-                
-                buf.append ("] ");
-            }
-
-            final PrintWriter out = m_out;
-
-            if (msg != null) buf.append (msg);
-            
-            out.println (buf);
-            if (FLUSH_LOG) out.flush ();
-        }
-    }
-    
-    private void _log (final int level, final String method,
-                       final String msg, final Throwable throwable)
-    {        
-        if ((level <= m_level) && (level >= SEVERE))
-        {
-            final Class caller = ClassLoaderResolver.getCallerClass (2);
-            final StringBuffer buf = new StringBuffer (m_prefix != null ? m_prefix + ": " : "");
-            
-            if ((caller != null) || (method != null))
-            {
-                buf.append ("[");
-                
-                if (caller != null) // if the caller could not be determined, s_classMask is ignored
-                {
-                    String callerName = caller.getName ();
-                    
-                    if (callerName.startsWith (PREFIX_TO_STRIP))
-                        callerName = callerName.substring (PREFIX_TO_STRIP_LENGTH);
-                        
-                    String parentName = callerName;
-                    
-                    final int firstDollar = callerName.indexOf ('$');
-                    if (firstDollar > 0) parentName = callerName.substring (0, firstDollar);
-                    
-                    if ((m_classMask == null) || m_classMask.contains (parentName))
-                        buf.append (callerName);
-                    else
-                        return;
-                }
-                
-                if (method != null)
-                {
-                    buf.append ("::");
-                    buf.append (method);
-                }
-                
-                buf.append ("] ");
-            }
-            
-            final PrintWriter out = m_out;
-            
-            if (msg != null) buf.append (msg);
-            
-            if (throwable != null)
-            {
-                final StringWriter sw = new StringWriter ();
-                final PrintWriter pw = new PrintWriter (sw);
-                
-                throwable.printStackTrace (pw);
-                pw.flush ();
-                
-                buf.append (sw.toString ());
-            }
-
-            out.println (buf);
-            if (FLUSH_LOG) out.flush ();
-        }
-    }
-
-    
-
-    private final int m_level; // always in [NONE, ALL] range
-    private final PrintWriter m_out; // never null
-    private final String m_prefix; // null is equivalent to no prefix
-    private final Set /* String */ m_classMask; // null is equivalent to no class filtering
-
-    private static final String PREFIX_TO_STRIP = "com.vladium."; // TODO: can this be set programmatically ?
-    private static final int PREFIX_TO_STRIP_LENGTH = PREFIX_TO_STRIP.length ();
-    private static final boolean FLUSH_LOG = true;
-    private static final String COMMA_DELIMITERS    = "," + Strings.WHITE_SPACE;
-
-    private static final Logger STATIC_LOGGER; // set in <clinit>
-    private static final ThreadLocalStack THREAD_LOCAL_STACK; // set in <clinit>
-    
-    static
-    {
-        THREAD_LOCAL_STACK = new ThreadLocalStack ();
-        
-        // TODO: unfortunately, this init code makes Logger coupled to the app classes
-        // (via the app namespace string constants)
-        // I don't quite see an elegant solution to this design problem yet
-        
-        final Properties properties = Property.getAppProperties (IAppConstants.APP_NAME_LC, Logger.class.getClassLoader ());
-        
-        // verbosity level:
-        
-        final int level;
-        {
-            final String _level = properties.getProperty (AppLoggers.PROPERTY_VERBOSITY_LEVEL,
-                                                          AppLoggers.DEFAULT_VERBOSITY_LEVEL);
-            level = stringToLevel (_level);
-        }
-        
-        // verbosity filter:
-        
-        final Set filter;
-        {
-            final String _filter = properties.getProperty (AppLoggers.PROPERTY_VERBOSITY_FILTER);
-            Set temp = null;
-            
-            if (_filter != null)
-            {
-                final StringTokenizer tokenizer = new StringTokenizer (_filter, COMMA_DELIMITERS);
-                if (tokenizer.countTokens () > 0)
-                {
-                    temp = new HashSet (tokenizer.countTokens ());
-                    while (tokenizer.hasMoreTokens ())
-                    {
-                        temp.add (tokenizer.nextToken ());
-                    }
-                }
-            }
-            
-            filter = temp;
-        }
-        
-        
-        STATIC_LOGGER = create (level,
-                                new PrintWriter (System.out, false),
-                                IAppConstants.APP_NAME,
-                                filter);
-    }
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/ByteArrayIStream.java b/core/java12/com/vladium/util/ByteArrayIStream.java
deleted file mode 100644
index 81b8d81..0000000
--- a/core/java12/com/vladium/util/ByteArrayIStream.java
+++ /dev/null
@@ -1,125 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ByteArrayIStream.java,v 1.1.1.1 2004/05/09 16:57:51 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.InputStream;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * An unsynchronized version of java.io.ByteArrayInputStream.<p>
- * 
- * All argument validation is disabled in release mode.<p>
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class ByteArrayIStream extends InputStream
-{
-    // public: ................................................................
-
-
-    public ByteArrayIStream (final byte [] buf)
-    {
-        this (buf, buf.length);
-    }
-
-    public ByteArrayIStream (final byte [] buf, final int length)
-    {
-        if ($assert.ENABLED) $assert.ASSERT ((length >= 0) && (length <= buf.length),
-            "invalid length: " + length);
-        
-        m_buf = buf;
-        m_max = length;
-    }    
-
-    // InputStream:
-    
-    public final int read ()
-    {
-        if (m_pos >= m_max)
-            return -1;
-        else
-            return 0xFF & m_buf [m_pos ++];
-    }
-
-    public final int read (final byte [] buf, final int offset, int length)
-    {
-        if ($assert.ENABLED)
-            $assert.ASSERT ((offset >= 0) && (offset <= buf.length) &&
-                (length >= 0) && ((offset + length) <= buf.length),
-                "invalid input (" + buf.length + ", " + offset + ", " + length + ")");
-        
-        final int pos = m_pos;
-        final int max = m_max;
-        
-        if (pos >= max) return -1;
-        if (pos + length > max) length = max - pos;
-        if (length <= 0) return 0;
-        
-        final byte [] mbuf = m_buf;
-        
-        if (length < NATIVE_COPY_THRESHOLD)
-            for (int i = 0; i < length; ++ i) buf [offset + i] = mbuf [pos + i];
-        else
-            System.arraycopy (mbuf, pos, buf, offset, length);
-            
-        m_pos += length;
-        
-        return length;
-    }
-    
-    public final int available ()
-    {
-        return m_max - m_pos;
-    }
-    
-    public final long skip (long n)
-    {
-        if (m_pos + n > m_max) n = m_max - m_pos;
-
-        if (n < 0) return 0;        
-        m_pos += n;
-        
-        return n;
-    }
-    
-    /**
-     * Differs from the contruct for InputStream.reset() in that this method
-     * always resets the stream to the same it was immediately after creation.
-     */
-    public final void reset ()
-    {
-        m_pos = 0;
-    }
-
-    /**
-     * Equivalent to {@link #reset()}. 
-     */
-    public final void close ()
-    {
-        reset ();
-    }
-
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private final byte [] m_buf;
-    private final int m_max;
-    private int m_pos;
-
-    private static final int NATIVE_COPY_THRESHOLD  = 9;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/ByteArrayOStream.java b/core/java12/com/vladium/util/ByteArrayOStream.java
deleted file mode 100644
index 59526f9..0000000
--- a/core/java12/com/vladium/util/ByteArrayOStream.java
+++ /dev/null
@@ -1,320 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ByteArrayOStream.java,v 1.1.1.1 2004/05/09 16:57:52 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.IOException;
-import java.io.OutputStream;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * An unsynchronized version of java.io.ByteArrayOutputStream that can expose
- * the underlying byte array without a defensive clone and can also be converted
- * to a {@link ByteArrayIStream} without intermediate array copies.<p> 
- * 
- * All argument validation is disabled in release mode.<p>
- * 
- * NOTE: copy-on-write not supported
- * 
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class ByteArrayOStream extends OutputStream
-{
-    // public: ................................................................
-    
-    /**
-     * Callee takes ownership of 'buf'.
-     */
-    public ByteArrayOStream (final int initialCapacity)
-    {
-        if ($assert.ENABLED)
-            $assert.ASSERT (initialCapacity >= 0, "negative initial capacity: " + initialCapacity); 
-        
-        m_buf = new byte [initialCapacity];
-    }
-    
-    public final ByteArrayIStream toByteIStream ()
-    {
-        return new ByteArrayIStream (m_buf, m_pos);
-    }
-    
-    public final void write2 (final int b1, final int b2)
-    {
-        final int pos = m_pos;
-        final int capacity = pos + 2;
-        byte [] mbuf = m_buf;
-        final int mbuflen = mbuf.length;
-        
-        if (mbuflen < capacity)
-        {
-            final byte [] newbuf = new byte [Math.max (mbuflen << 1, capacity)];
-        
-            if (pos < NATIVE_COPY_THRESHOLD)
-                for (int i = 0; i < pos; ++ i) newbuf [i] = mbuf [i];
-            else
-                System.arraycopy (mbuf, 0, newbuf, 0, pos);
-            
-            m_buf = mbuf = newbuf;
-        }
-        
-        mbuf [pos] = (byte) b1;
-        mbuf [pos + 1] = (byte) b2;
-        m_pos = capacity;
-    }
-    
-    public final void write3 (final int b1, final int b2, final int b3)
-    {
-        final int pos = m_pos;
-        final int capacity = pos + 3;
-        byte [] mbuf = m_buf;
-        final int mbuflen = mbuf.length;
-        
-        if (mbuflen < capacity)
-        {
-            final byte [] newbuf = new byte [Math.max (mbuflen << 1, capacity)];
-        
-            if (pos < NATIVE_COPY_THRESHOLD)
-                for (int i = 0; i < pos; ++ i) newbuf [i] = mbuf [i];
-            else
-                System.arraycopy (mbuf, 0, newbuf, 0, pos);
-            
-            m_buf = mbuf = newbuf;
-        }
-        
-        mbuf [pos] = (byte) b1;
-        mbuf [pos + 1] = (byte) b2;
-        mbuf [pos + 2] = (byte) b3;
-        m_pos = capacity;
-    }
-    
-    public final void write4 (final int b1, final int b2, final int b3, final int b4)
-    {
-        final int pos = m_pos;
-        final int capacity = pos + 4;
-        byte [] mbuf = m_buf;
-        final int mbuflen = mbuf.length;
-        
-        if (mbuflen < capacity)
-        {
-            final byte [] newbuf = new byte [Math.max (mbuflen << 1, capacity)];
-        
-            if (pos < NATIVE_COPY_THRESHOLD)
-                for (int i = 0; i < pos; ++ i) newbuf [i] = mbuf [i];
-            else
-                System.arraycopy (mbuf, 0, newbuf, 0, pos);
-            
-            m_buf = mbuf = newbuf;
-        }
-        
-        mbuf [pos] = (byte) b1;
-        mbuf [pos + 1] = (byte) b2;
-        mbuf [pos + 2] = (byte) b3;
-        mbuf [pos + 3] = (byte) b4;
-        m_pos = capacity;
-    }
-    
-    public final void writeTo (final OutputStream out)
-        throws IOException
-    {
-        out.write (m_buf, 0, m_pos);
-    }
-    
-//    public final void readFully (final InputStream in)
-//        throws IOException
-//    {
-//        while (true)
-//        {
-//            int chunk = in.available ();
-//            
-//            System.out.println ("available = " + chunk);
-//            
-//            // TODO: this case is handled poorly (on EOF)
-//            if (chunk == 0) chunk = READ_CHUNK_SIZE;
-//            
-//            // read at least 'available' bytes: extend the capacity as needed
-//        
-//            int free = m_buf.length - m_pos;
-//            
-//            final int read;
-//            if (free > chunk)
-//            {
-//                // try reading more than 'chunk' anyway:
-//                read = in.read (m_buf, m_pos, free);
-//            }
-//            else
-//            {
-//                // extend the capacity to match 'chunk':
-//                {
-//                    System.out.println ("reallocation");
-//                    final byte [] newbuf = new byte [m_pos + chunk];
-//            
-//                    if (m_pos < NATIVE_COPY_THRESHOLD)
-//                        for (int i = 0; i < m_pos; ++ i) newbuf [i] = m_buf [i];
-//                    else
-//                        System.arraycopy (m_buf, 0, newbuf, 0, m_pos);
-//                
-//                    m_buf = newbuf;
-//                }
-//                
-//                read = in.read (m_buf, m_pos, chunk);
-//            }
-//
-//            if (read < 0)
-//                break;
-//            else
-//                m_pos += read;
-//        }
-//    }
-    
-//    public final void addCapacity (final int extraCapacity)
-//    {
-//        final int pos = m_pos;
-//        final int capacity = pos + extraCapacity;
-//        byte [] mbuf = m_buf;
-//        final int mbuflen = mbuf.length;
-//        
-//        if (mbuflen < capacity)
-//        {
-//            final byte [] newbuf = new byte [Math.max (mbuflen << 1, capacity)];
-//        
-//            if (pos < NATIVE_COPY_THRESHOLD)
-//                for (int i = 0; i < pos; ++ i) newbuf [i] = mbuf [i];
-//            else
-//                System.arraycopy (mbuf, 0, newbuf, 0, pos);
-//            
-//            m_buf = newbuf;
-//        }
-//    }
-    
-    public final byte [] getByteArray ()
-    {
-        return m_buf;
-    }
-
-    /**
-     * 
-     * @return [result.length = size()]
-     */    
-    public final byte [] copyByteArray ()
-    {
-        final int pos = m_pos;
-        
-        final byte [] result = new byte [pos];
-        final byte [] mbuf = m_buf;
-        
-        if (pos < NATIVE_COPY_THRESHOLD)
-            for (int i = 0; i < pos; ++ i) result [i] = mbuf [i];
-        else
-            System.arraycopy (mbuf, 0, result, 0, pos);
-        
-        return result;
-    }
-    
-    public final int size ()
-    {
-        return m_pos;
-    }
-    
-    public final int capacity ()
-    {
-        return m_buf.length;
-    }
-    
-    /**
-     * Does not reduce the current capacity.
-     */
-    public final void reset ()
-    {
-        m_pos = 0;
-    }
-    
-    // OutputStream:
-    
-    public final void write (final int b)
-    {
-        final int pos = m_pos;
-        final int capacity = pos + 1;
-        byte [] mbuf = m_buf;
-        final int mbuflen = mbuf.length;
-        
-        if (mbuflen < capacity)
-        {
-            final byte [] newbuf = new byte [Math.max (mbuflen << 1, capacity)];
-            
-            if (pos < NATIVE_COPY_THRESHOLD)
-                for (int i = 0; i < pos; ++ i) newbuf [i] = mbuf [i];
-            else
-                System.arraycopy (mbuf, 0, newbuf, 0, pos);
-            
-            m_buf = mbuf = newbuf;
-        }
-        
-        mbuf [pos] = (byte) b;
-        m_pos = capacity;
-    }
-
-
-    public final void write (final byte [] buf, final int offset, final int length)
-    {
-        if ($assert.ENABLED)
-            $assert.ASSERT ((offset >= 0) && (offset <= buf.length) &&
-                (length >= 0) && ((offset + length) <= buf.length),
-                "invalid input (" + buf.length + ", " + offset + ", " + length + ")");
-        
-        final int pos = m_pos;
-        final int capacity = pos + length;
-        byte [] mbuf = m_buf;
-        final int mbuflen = mbuf.length;
-        
-        if (mbuflen < capacity)
-        {
-            final byte [] newbuf = new byte [Math.max (mbuflen << 1, capacity)];
-            
-            if (pos < NATIVE_COPY_THRESHOLD)
-                for (int i = 0; i < pos; ++ i) newbuf [i] = mbuf [i];
-            else
-                System.arraycopy (mbuf, 0, newbuf, 0, pos);
-            
-            m_buf = mbuf = newbuf;
-        }
-        
-        if (length < NATIVE_COPY_THRESHOLD)
-            for (int i = 0; i < length; ++ i) mbuf [pos + i] = buf [offset + i];
-        else
-            System.arraycopy (buf, offset, mbuf, pos, length);
-            
-        m_pos = capacity; 
-    }
-
-    
-    /**
-     * Equivalent to {@link #reset()}. 
-     */
-    public final void close ()
-    {
-        reset ();
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private byte [] m_buf;
-    private int m_pos;
-    
-//    private static final int READ_CHUNK_SIZE        = 16 * 1024;
-    private static final int NATIVE_COPY_THRESHOLD  = 9;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/ClassLoadContext.java b/core/java12/com/vladium/util/ClassLoadContext.java
deleted file mode 100644
index 39802dc..0000000
--- a/core/java12/com/vladium/util/ClassLoadContext.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ClassLoadContext.java,v 1.1.1.1 2004/05/09 16:57:52 vlad_r Exp $
- */
-package com.vladium.util;
-
-// ----------------------------------------------------------------------------
-/**
- * Information context for {@link IClassLoadStrategy#getClassLoader(ClassLoadContext)}.
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-class ClassLoadContext
-{
-    // public: ................................................................
-    
-    
-    /**
-     * Returns the class representing the caller of {@link ClassLoaderResolver}
-     * API. Can be used to retrieve the caller's classloader etc (which may be
-     * different from the ClassLoaderResolver's own classloader) ['null' if caller
-     * resolver could be instantiated due to security restrictions]. 
-     */
-    public final Class getCallerClass ()
-    {
-        return m_caller;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    /**
-     * This constructor is package-private to restrict instantiation to
-     * {@link ClassLoaderResolver} only.
-     * 
-     * @param caller [can be null]
-     */
-    ClassLoadContext (final Class caller)
-    {
-        m_caller = caller;
-    }
-    
-    // private: ...............................................................
-    
-
-    private final Class m_caller;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/ClassLoaderResolver.java b/core/java12/com/vladium/util/ClassLoaderResolver.java
deleted file mode 100644
index caa35a8..0000000
--- a/core/java12/com/vladium/util/ClassLoaderResolver.java
+++ /dev/null
@@ -1,228 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ClassLoaderResolver.java,v 1.1.1.1.2.2 2004/07/10 03:34:53 vlad_r Exp $
- */
-package com.vladium.util;
-
-// ----------------------------------------------------------------------------
-/**
- * This non-instantiable non-subclassable class acts as the global point for
- * choosing a ClassLoader for dynamic class/resource loading at any point
- * in an application.
- * 
- * @see ResourceLoader
- * @see IClassLoadStrategy
- * @see DefaultClassLoadStrategy
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class ClassLoaderResolver
-{
-    // public: ................................................................
-    
-    // NOTE: don't use Logger in this class to avoid infinite recursion
-
-    /**
-     * This method selects the "best" classloader instance to be used for
-     * class/resource loading by whoever calls this method. The decision
-     * typically involves choosing between the caller's current, thread context,
-     * system, and other classloaders in the JVM and is made by the {@link IClassLoadStrategy}
-     * instance established by the last call to {@link #setStrategy}.<P>
-     * 
-     * This method does not throw.
-     * 
-     * @param caller [null input eliminates the caller's current classloader
-     * from consideration]
-     * 
-     * @return classloader to be used by the caller ['null' indicates the
-     * primordial loader]
-     */
-    public static synchronized ClassLoader getClassLoader (final Class caller)
-    {
-        final ClassLoadContext ctx = new ClassLoadContext (caller);
-        
-        return s_strategy.getClassLoader (ctx); 
-    }
-
-    /**
-     * This method selects the "best" classloader instance to be used for
-     * class/resource loading by whoever calls this method. The decision
-     * typically involves choosing between the caller's current, thread context,
-     * system, and other classloaders in the JVM and is made by the {@link IClassLoadStrategy}
-     * instance established by the last call to {@link #setStrategy}.<P>
-     * 
-     * This method uses its own caller to set the call context. To be able to
-     * override this decision explicitly, use {@link #getClassLoader(Class)}.<P> 
-     * 
-     * This method does not throw.
-     * 
-     * @return classloader to be used by the caller ['null' indicates the
-     * primordial loader]
-     */
-    public static synchronized ClassLoader getClassLoader ()
-    {
-        final Class caller = getCallerClass (1); // 'caller' can be set to null
-        final ClassLoadContext ctx = new ClassLoadContext (caller);
-        
-        return s_strategy.getClassLoader (ctx); 
-    }
-
-    /*
-     * Indexes into the current method call context with a given offset. Offset 0
-     * corresponds to the immediate caller, offset 1 corresponds to its caller,
-     * etc.<P>
-     * 
-     * Invariant: getCallerClass(0) == class containing code that performs this call 
-     */
-    public static Class getCallerClass (final int callerOffset)
-    {
-        if (CALLER_RESOLVER == null) return null; // only happens if <clinit> failed
-
-        return CALLER_RESOLVER.getClassContext () [CALL_CONTEXT_OFFSET + callerOffset];
-    }
-
-    /**
-     * Returns 'true' if 'loader2' is a delegation child of 'loader1' [or if
-     * 'loader1'=='loader2']. Of course, this works only for classloaders that
-     * set their parent pointers correctly. 'null' is interpreted as the
-     * primordial loader [i.e., everybody's parent].
-     */ 
-    public static boolean isChild (final ClassLoader loader1, ClassLoader loader2)
-    {
-        if (loader1 == loader2) return true; 
-        if (loader2 == null) return false; 
-        if (loader1 == null) return true;
-        
-        for ( ; loader2 != null; loader2 = loader2.getParent ())
-        {
-            if (loader2 == loader1) return true;
-        }   
-
-        return false;
-    }
-
-    /**
-     * Gets the current classloader selection strategy setting. 
-     */
-    public static synchronized IClassLoadStrategy getStrategy ()
-    {
-        return s_strategy;
-    }
-
-    /**
-     * Sets the classloader selection strategy to be used by subsequent calls
-     * to {@link #getClassLoader()}. An instance of {@link ClassLoaderResolver.DefaultClassLoadStrategy}
-     * is in effect if this method is never called.
-     *  
-     * @param strategy new strategy [may not be null] 
-     * @return previous setting
-     */    
-    public static synchronized IClassLoadStrategy setStrategy (final IClassLoadStrategy strategy)
-    {
-        if (strategy == null) throw new IllegalArgumentException ("null input: strategy");
-        
-        final IClassLoadStrategy old = s_strategy;
-        s_strategy = strategy;
-        
-        return old;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final class DefaultClassLoadStrategy implements IClassLoadStrategy
-    {
-        public ClassLoader getClassLoader (final ClassLoadContext ctx)
-        {
-            if (ctx == null) throw new IllegalArgumentException ("null input: ctx");
-            
-            final Class caller = ctx.getCallerClass ();
-            final ClassLoader contextLoader = Thread.currentThread ().getContextClassLoader ();
-            
-            ClassLoader result;
-            
-            if (caller == null)
-                result = contextLoader;
-            else
-            {
-                final ClassLoader callerLoader = caller.getClassLoader ();
-                
-                // if 'callerLoader' and 'contextLoader' are in a parent-child
-                // relationship, always choose the child:
-                
-                // SF BUG 975080: change the sibling case to use 'callerLoader'
-                // to work around ANT 1.6.x incorrect classloading model:
-                
-                if (isChild (callerLoader, contextLoader))
-                    result = contextLoader;
-                else
-                    result = callerLoader;
-            }
-            
-            final ClassLoader systemLoader = ClassLoader.getSystemClassLoader ();
-            
-            // precaution for when deployed as a bootstrap or extension class:
-            if (isChild (result, systemLoader))
-                result = systemLoader;
-            
-            return result;
-        }
-    
-    } // end of nested class
-    
-    
-    /**
-     * A helper class to get the call context. It subclasses SecurityManager
-     * to make getClassContext() accessible. An instance of CallerResolver
-     * only needs to be created, not installed as an actual security
-     * manager.
-     */
-    private static final class CallerResolver extends SecurityManager
-    {
-        protected Class [] getClassContext ()
-        {
-            return super.getClassContext ();
-        }
-        
-    } // end of nested class 
-    
-    
-    private ClassLoaderResolver () {} // prevent subclassing
-
-    
-    private static IClassLoadStrategy s_strategy; // initialized in <clinit>
-    
-    private static final int CALL_CONTEXT_OFFSET = 2; // may need to change if this class is redesigned
-    private static final CallerResolver CALLER_RESOLVER; // set in <clinit>
-    //private static Throwable CLINIT_FAILURE;
-    
-    static
-    {
-        CallerResolver temp = null;
-        try
-        {
-            // this can fail if the current SecurityManager does not allow
-            // RuntimePermission ("createSecurityManager"):
-            
-            temp = new CallerResolver ();
-        }
-        catch (Throwable t)
-        {
-            //CLINIT_FAILURE = t;
-        }
-        CALLER_RESOLVER = temp;
-        
-        s_strategy = new DefaultClassLoadStrategy ();
-    }
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/Descriptors.java b/core/java12/com/vladium/util/Descriptors.java
deleted file mode 100644
index de8b4aa..0000000
--- a/core/java12/com/vladium/util/Descriptors.java
+++ /dev/null
@@ -1,239 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Descriptors.java,v 1.1.1.1 2004/05/09 16:57:52 vlad_r Exp $
- */
-package com.vladium.util;
-
-import com.vladium.jcd.cls.IClassDefConstants;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class Descriptors
-{
-    // public: ................................................................
-
-    // TODO: some overlap with Types in c.v.jcp.lib
-    
-    public static final char JAVA_NAME_SEPARATOR = '.';
-    public static final char VM_NAME_SEPARATOR = '/';
-    
-    public static String combine (final String packageName, final String name, final char separator)
-    {
-        if ((name == null) || (name.length () == 0))
-            throw new IllegalArgumentException ("null or empty input: name");
-            
-        if ((packageName == null) || (packageName.length () == 0))
-            return name;
-        else
-            return new StringBuffer (packageName).append (separator).append (name).toString ();
-    }
-    
-    public static String combineJavaName (final String packageName, final String name)
-    {
-        return combine (packageName, name, JAVA_NAME_SEPARATOR);
-    }
-    
-    public static String combineVMName (final String packageName, final String name)
-    {
-        return combine (packageName, name, VM_NAME_SEPARATOR);
-    }
-    
-    /**
-     * Converts a Java package/class name to how it would be
-     * represented in the VM.<P>
-     * 
-     * Example:
-     * <PRE><CODE>
-     * javaNameToVMName("java.lang.Object") = "java/lang/Object"
-     * </CODE></PRE>
-     * 
-     * @see #vmNameToJavaName
-     */
-    public static String javaNameToVMName (final String javaName)
-    {
-        if (javaName == null) return null;
-        
-        return javaName.replace ('.', '/');
-    }
-    
-    /**
-     * Converts a JVM package/class name to how it would be
-     * represented in Java.<P>
-     * 
-     * Example:
-     * <PRE><CODE>
-     * vmNameToJavaName("java/lang/Object") = "java.lang.Object"
-     * </CODE></PRE>
-     * 
-     * @see #javaNameToVMName
-     */
-    public static String vmNameToJavaName (final String vmName)
-    {
-        if (vmName == null) return null;
-        
-        return vmName.replace ('/', '.');
-    }
-    
-    /**
-     * NOTE: With 'shortTypeNames'=true the output is potentially lossy (truncates
-     * package name) and can result in method signature collisions in very rare
-     * circumstances (e.g., java.awt.List = java.util.List).<P>
-     * 
-     * Return type info is also lost.
-     * 
-     * @return method name (signature), no package prefix, no return type
-     */
-    public static String methodVMNameToJavaName (final String className,
-                                                 final String methodVMName,
-                                                 final String descriptor,
-                                                 final boolean renameInits,
-                                                 final boolean shortTypeNames,
-                                                 final boolean appendReturnType)
-    {
-        final StringBuffer out = new StringBuffer ();
-        
-        if (renameInits)
-        {
-            if (IClassDefConstants.CLINIT_NAME.equals (methodVMName))
-                return "<static initializer>";
-            else if (IClassDefConstants.INIT_NAME.equals (methodVMName))
-                out.append (className);
-            else
-                out.append (methodVMName);
-        }
-        else
-        {
-            if (IClassDefConstants.CLINIT_NAME.equals (methodVMName))
-                return IClassDefConstants.CLINIT_NAME;
-            else
-                out.append (methodVMName);
-        }
-        
-        final char [] chars = descriptor.toCharArray ();
-        int end;
-        
-        out.append (" (");
-        {
-            for (end = chars.length; chars [-- end] != ')'; );
-            
-            for (int start = 1; start < end; )
-            {
-                if (start > 1) out.append (", ");
-                start = typeDescriptorToJavaName (chars, start, shortTypeNames, out);
-            }
-        }        
-        
-        if (appendReturnType)
-        {
-            out.append ("): ");
-            
-            typeDescriptorToJavaName (chars, end + 1, shortTypeNames, out);
-        }
-        else
-        {
-            out.append (')');
-        }
-        
-        return out.toString ();
-    }
-    
-    
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-//    private static int typeSignatureToJavaName (final char [] signature, int start,
-//                                                final boolean shortTypeNames,
-//                                                final StringBuffer out)
-//    {
-//        
-//    }
-
-
-    private static int typeDescriptorToJavaName (final char [] descriptor, int start,
-                                                 final boolean shortTypeNames,
-                                                 final StringBuffer out)
-    {
-        int dims;
-        for (dims = 0; descriptor [start] == '['; ++ dims, ++ start);
-        
-        char c = descriptor [start ++]; 
-        switch (c)
-        {
-            case 'L':
-            {
-                if (shortTypeNames)
-                {
-                    int lastSlash = -1;
-                    for (int s = start; descriptor [s] != ';'; ++ s)
-                    {
-                        if (descriptor [s] == '/') lastSlash = s;
-                    }
-                    
-                    for (start = lastSlash > 0 ? lastSlash + 1 : start; descriptor [start] != ';'; ++ start)
-                    {
-                        c = descriptor [start];
-                        if (RENAME_INNER_CLASSES)
-                            out.append (c != '$' ? c : '.');
-                        else
-                            out.append (c);
-                    }                        
-                }
-                else
-                {
-                    for (; descriptor [start] != ';'; ++ start)
-                    {
-                        c = descriptor [start];
-                        out.append (c != '/' ? c : '.');
-                    }
-                }
-                
-                ++ start;
-            }
-            break;
-            
-            case 'B': out.append ("byte"); break;
-            case 'C': out.append ("char"); break;
-            case 'D': out.append ("double"); break;
-            case 'F': out.append ("float"); break;
-            case 'I': out.append ("int"); break;
-            case 'J': out.append ("long"); break;
-            case 'S': out.append ("short"); break;
-            case 'Z': out.append ("boolean"); break;
-            
-            case 'V': out.append ("void"); break;
-            
-            default:          
-                throw new IllegalStateException ("unknown type descriptor element: " + c);
-                
-        } // end of switch
-        
-        if (dims > 0)
-        {
-            out.append (' ');
-            for (int d = 0; d < dims; ++ d) out.append ("[]");
-        }
-        
-        return start;
-    }
-
-    
-    private Descriptors () {} // prevent subclassing
-    
-    
-    // note: setting this to 'true' is not 100% reliable because it is legal
-    // to have $'s in regular class names as well:
-    private static final boolean RENAME_INNER_CLASSES = false;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/Files.java b/core/java12/com/vladium/util/Files.java
deleted file mode 100644
index 4ef3a3e..0000000
--- a/core/java12/com/vladium/util/Files.java
+++ /dev/null
@@ -1,338 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Files.java,v 1.1.1.1.2.1 2004/07/09 01:28:37 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.BufferedReader;
-import java.io.File;
-import java.io.FileReader;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.HashSet;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Set;
-import java.util.StringTokenizer;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class Files
-{
-    // public: ................................................................
-    
-    /**
-     * No duplicate elimination.
-     * 
-     * @param atfile
-     */
-    public static String [] readFileList (final File atfile)
-        throws IOException
-    {
-        if (atfile == null) throw new IllegalArgumentException ("null input: atfile");
-        
-        List _result = null;
-        
-        BufferedReader in = null;
-        try
-        {
-            in = new BufferedReader (new FileReader (atfile), 8 * 1024); // uses default encoding
-            _result = new LinkedList ();
-            
-            for (String line; (line = in.readLine ()) != null; )
-            {
-                line = line.trim ();
-                if ((line.length () == 0) || (line.charAt (0) == '#')) continue;
-                
-                _result.add (line);
-            }
-        }
-        finally
-        {
-            if (in != null) try { in.close (); } catch (Exception ignore) {}
-        }
-        
-        if ((_result == null) || _result.isEmpty ())
-            return IConstants.EMPTY_STRING_ARRAY;
-        else
-        {
-            final String [] result = new String [_result.size ()];
-            _result.toArray (result);
-            
-            return result;
-        }
-    }
-    
-    /**
-     * Converts an array of path segments to an array of Files. The order
-     * of files follows the original order of path segments, except "duplicate"
-     * entries are removed. The definition of duplicates depends on 'canonical':
-     * <ul>
-     *  <li> if 'canonical'=true, the pathnames are canonicalized via {@link #canonicalizePathname}
-     *  before they are compared for equality
-     *  <li> if 'canonical'=false, the pathnames are compared as case-sensitive strings
-     * </ul>
-     * 
-     * Note that duplicate removal in classpaths affects ClassLoader.getResources().
-     * The first mode above makes the most sense, however the last one is what
-     * Sun's java.net.URLClassLoader appears to do. Hence the last mode might be
-     * necessary for reproducing its behavior in Sun-compatible JVMs.  
-     */    
-    public static File [] pathToFiles (final String [] path, final boolean canonical)
-    {
-        if (path == null) throw new IllegalArgumentException ("null input: path");
-        if (path.length == 0) return IConstants.EMPTY_FILE_ARRAY;
-        
-        final List /* Files */ _result = new ArrayList (path.length);
-        final Set /* String */ pathnames = new HashSet (path.length);
-        
-        final String separators = ",".concat (File.pathSeparator);
-        
-        for (int i = 0; i < path.length; ++ i)
-        {
-            String segment = path [i];
-            if (segment == null) throw new IllegalArgumentException ("null input: path[" + i + "]");
-            
-            final StringTokenizer tokenizer = new StringTokenizer (segment, separators);
-            while (tokenizer.hasMoreTokens ())
-            {
-                String pathname = tokenizer.nextToken ();
-            
-                if (canonical) pathname = canonicalizePathname (pathname);
-                
-                if (pathnames.add (pathname))
-                {
-                    _result.add (new File (pathname));
-                }
-            }
-        }
-        
-        final File [] result = new File [_result.size ()];
-        _result.toArray (result);
-        
-        return result;
-    }
-    
-    /**
-     * Converts 'pathname' into the canonical OS form. This wrapper function
-     * will return the absolute form of 'pathname' if File.getCanonicalPath() fails.
-     */
-    public static String canonicalizePathname (final String pathname)
-    {
-        if (pathname == null) throw new IllegalArgumentException ("null input: pathname");
-        
-        try
-        {
-            return new File (pathname).getCanonicalPath ();
-        }
-        catch (Exception e)
-        {
-            return new File (pathname).getAbsolutePath ();
-        }
-    }
-    
-    public static File canonicalizeFile (final File file)
-    {
-        if (file == null) throw new IllegalArgumentException ("null input: file");
-        
-        try
-        {
-            return file.getCanonicalFile ();
-        }
-        catch (Exception e)
-        {
-            return file.getAbsoluteFile ();
-        }
-    }
-
-    /**
-     * Invariant: (getFileName (file) + getFileExtension (file)).equals (file.getName ()).
-     * 
-     * @param file File input file descriptor [must be non-null]
-     * 
-     * @return String file name without the extension [excluding '.' separator]
-     * [if 'file' does not appear to have an extension, the full name is returned].
-     * 
-     * @throws IllegalArgumentException if 'file' is null
-     */ 
-    public static String getFileName (final File file)
-    {
-        if (file == null) throw new IllegalArgumentException ("null input: file");
-        
-        final String name = file.getName ();
-        int lastDot = name.lastIndexOf ('.');
-        if (lastDot < 0) return name;
-        
-        return name.substring (0, lastDot);
-    }
-    
-    /**
-     * Invariant: (getFileName (file) + getFileExtension (file)).equals (file.getName ()).
-     * 
-     * @param file File input file descriptor [must be non-null]
-     * 
-     * @return String extension [including '.' separator] or "" if 'file' does not
-     * appear to have an extension.
-     * 
-     * @throws IllegalArgumentException if 'file' is null
-     */
-    public static String getFileExtension (final File file)
-    {
-        if (file == null) throw new IllegalArgumentException ("null input: file");
-        
-        final String name = file.getName ();
-        int lastDot = name.lastIndexOf ('.');
-        if (lastDot < 0) return "";
-        
-        return name.substring (lastDot);
-    }
-    
-    /**
-     * 
-     * @param dir [null is ignored]
-     * @param file [absolute overrides 'dir']
-     * @return
-     */
-    public static File newFile (final File dir, final File file)
-    {
-        if (file == null) throw new IllegalArgumentException ("null input: file");
-        
-        if ((dir == null) || file.isAbsolute ()) return file;
-        
-        return new File (dir, file.getPath ());
-    }
-    
-    /**
-     * 
-     * @param dir [null is ignored]
-     * @param file [absolute overrides 'dir']
-     * @return
-     */
-    public static File newFile (final File dir, final String file)
-    {
-        if (file == null) throw new IllegalArgumentException ("null input: file");
-        
-        final File fileFile  = new File (file);
-        if ((dir == null) || fileFile.isAbsolute ()) return fileFile;
-        
-        return new File (dir, file);
-    }
-    
-    /**
-     * 
-     * @param dir [null is ignored]
-     * @param file [absolute overrides 'dir']
-     * @return
-     */
-    public static File newFile (final String dir, final String file)
-    {
-        if (file == null) throw new IllegalArgumentException ("null input: file");
-        
-        final File fileFile  = new File (file);
-        if ((dir == null) || fileFile.isAbsolute ()) return fileFile;
-        
-        return new File (dir, file);
-    }
-    
-    /**
-     * Renames 'source' to 'target' [intermediate directories are created if necessary]. If
-     * 'target' exists and 'overwrite' is false, the method is a no-op. No exceptions are
-     * thrown except for when input is invalid. If the operation fails half-way it can leave
-     * some file system artifacts behind.
-     * 
-     * @return true iff the renaming was actually performed. 
-     * 
-     * @param source file descriptor [file must exist]
-     * @param target target file descriptor [an existing target may get deleted
-     * if 'overwrite' is true]
-     * @param overwrite if 'true', forces an existing target to be deleted 
-     * 
-     * @throws IllegalArgumentException if 'source' is null or file does not exist
-     * @throws IllegalArgumentException if 'target' is null
-     */     
-    public static boolean renameFile (final File source, final File target, final boolean overwrite)
-    {
-        if ((source == null) || ! source.exists ())
-            throw new IllegalArgumentException ("invalid input source: [" + source + "]");
-        if (target == null)
-            throw new IllegalArgumentException ("null input: target");
-        
-        final boolean targetExists;
-        if (! (targetExists = target.exists ()) || overwrite)
-        {
-            if (targetExists)
-            {
-                // need to delete the target first or the rename will fail:
-                target.delete (); // not checking the result here: let the rename fail later
-            }
-            else
-            {
-                // note that File.renameTo() does not create intermediate directories on demand:
-                final File targetDir = target.getParentFile ();
-                if ((targetDir != null) && ! targetDir.equals (source.getParentFile ()))
-                    targetDir.mkdirs (); // TODO: clean this up on failure?
-            }
-            
-            // note: this can fail for a number of reasons, including the target
-            // being on a different drive/file system:
-            return source.renameTo (target);
-        }
-        
-        return false;
-    }
-    
-    /**
-     * A slightly stricter version of File.createTempFile() in J2SDK 1.3: it requires
-     * that the caller provide an existing parent directory for the temp file.
-     * This defers to File.createTempFile (prefix, extension, parentDir) after
-     * normalizing 'extension'.<P>
-     * 
-     * MT-safety: if several threads use this API concurrently, the temp files
-     * created are guaranteed to get created without any collisions and correspond
-     * to files that did not exist before. However, if such a temp file is deleted
-     * at a later point, this method may reuse its file name. These MT-safety
-     * guarantees do not hold if files are created in the same directory outside
-     * of this method.
-     * 
-     * @param parentDir parent dir for the temp file [may not be null and must exist]
-     * @param prefix prefix pattern for the temp file name [only the first 3
-     * chars are guaranteed to be used]
-     * @param extension pattern for the temp file name [null is equivalient to
-     * ".tmp"; this is always normalized to start with "."; only the first 3
-     * non-"." chars are guaranteed to be used]
-     * 
-     * @return writeable temp file descriptor [incorporates 'parentDir' in its pathname]
-     * @throws IOException if a temp file could not be created
-     */
-    public static File createTempFile (final File parentDir, final String prefix, String extension)
-        throws IOException
-    {
-        if ((parentDir == null) || ! parentDir.exists ())
-            throw new IllegalArgumentException ("invalid parent directory: [" + parentDir + "]");
-        if ((prefix == null) || (prefix.length () < 3))
-            throw new IllegalArgumentException ("null or less than 3 chars long: " + prefix);
-        
-        if (extension == null) extension = ".tmp";
-        else if (extension.charAt (0) != '.') extension = ".".concat (extension);
-        
-        return File.createTempFile (prefix, extension, parentDir);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private Files () {} // prevent subclassing
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/IClassLoadStrategy.java b/core/java12/com/vladium/util/IClassLoadStrategy.java
deleted file mode 100644
index d5a02b4..0000000
--- a/core/java12/com/vladium/util/IClassLoadStrategy.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IClassLoadStrategy.java,v 1.1.1.1 2004/05/09 16:57:52 vlad_r Exp $
- */
-package com.vladium.util;
-
-// ----------------------------------------------------------------------------
-/**
- * The interface implemented by any classloader selection Strategy used
- * with {@link ClassLoaderResolver} API.
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IClassLoadStrategy
-{
-    // public: ................................................................
-    
-    /**
-     * Selects a classloader based on a given load context.
-     * 
-     * @see ClassLoaderResolver#getClassLoader()
-     */
-    ClassLoader getClassLoader (ClassLoadContext ctx);
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/IConstants.java b/core/java12/com/vladium/util/IConstants.java
deleted file mode 100644
index 4b661ed..0000000
--- a/core/java12/com/vladium/util/IConstants.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IConstants.java,v 1.1.1.1 2004/05/09 16:57:52 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.File;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IConstants
-{
-    // public: ................................................................
-    
-    String [] EMPTY_STRING_ARRAY = new String [0];
-    File [] EMPTY_FILE_ARRAY = new File [0];
-    int [] EMPTY_INT_ARRAY = new int [0];
-    
-    String EOL = System.getProperty ("line.separator", "\n");
-    
-    String INDENT_INCREMENT = "  ";
-
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/IPathEnumerator.java b/core/java12/com/vladium/util/IPathEnumerator.java
deleted file mode 100644
index 8f5c8bc..0000000
--- a/core/java12/com/vladium/util/IPathEnumerator.java
+++ /dev/null
@@ -1,334 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IPathEnumerator.java,v 1.1.1.1.2.1 2004/07/16 23:32:04 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.BufferedInputStream;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.FileNotFoundException;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.HashSet;
-import java.util.Set;
-import java.util.StringTokenizer;
-import java.util.jar.Attributes;
-import java.util.jar.JarFile;
-import java.util.jar.JarInputStream;
-import java.util.jar.Manifest;
-import java.util.zip.ZipEntry;
-
-import com.vladium.logging.Logger;
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IPathEnumerator
-{
-    // public: ................................................................
-    
-    // TODO: archives inside archives? (.war ?)
-    
-    public static interface IPathHandler
-    {
-        void handleDirStart (File pathDir, File dir); // not generated for path dirs themselves
-        void handleFile (File pathDir, File file); 
-        void handleDirEnd (File pathDir, File dir);
-
-        /**
-         * Called just after the enumerator's zip input stream for this archive
-         * is opened and the manifest entry is read.
-         */        
-        void handleArchiveStart (File parentDir, File archive, Manifest manifest);
-        
-        void handleArchiveEntry (JarInputStream in, ZipEntry entry);
-        
-        /**
-         * Called after the enumerator's zip input stream for this archive
-         * has been closed.
-         */
-        void handleArchiveEnd (File parentDir, File archive);
-        
-    } // end of nested interface
-    
-    
-    void enumerate () throws IOException;
-
-    
-    public static abstract class Factory
-    {
-        public static IPathEnumerator create (final File [] path, final boolean canonical, final IPathHandler handler)
-        {
-            return new PathEnumerator (path, canonical, handler);
-        }
-        
-        private static final class PathEnumerator implements IPathEnumerator
-        {
-            public void enumerate () throws IOException
-            {
-                final IPathHandler handler = m_handler;
-                
-                for (m_pathIndex = 0; m_pathIndex < m_path.size (); ++ m_pathIndex) // important not to cache m_path.size()
-                {
-                    final File f = (File) m_path.get (m_pathIndex);
-                    
-                    if (! f.exists ())
-                    {
-                        if (IGNORE_INVALID_ENTRIES)
-                            continue;
-                        else
-                            throw new IllegalArgumentException ("path entry does not exist: [" + f + "]");
-                    }
-                    
-                    
-                    if (f.isDirectory ())
-                    {
-                        if (m_verbose) m_log.verbose ("processing dir path entry [" + f.getAbsolutePath () + "] ...");
-                        
-                        m_currentPathDir = f;
-                        enumeratePathDir (null);
-                    }
-                    else
-                    {
-                        final String name = f.getName ();
-                        final String lcName = name.toLowerCase ();
-                        
-                        if (lcName.endsWith (".zip") || lcName.endsWith (".jar"))
-                        {
-                            if (m_verbose) m_log.verbose ("processing archive path entry [" + f.getAbsolutePath () + "] ...");
-                            
-                            final File parent = f.getParentFile (); // could be null
-                            final File archive = new File (name);
-                            m_currentPathDir = parent;
-                        
-                            // move to enumeratePathArchive(): handler.handleArchiveStart (parent, archive);
-                            enumeratePathArchive (name);
-                            handler.handleArchiveEnd (parent, archive); // note: it is important that this is called after the zip stream has been closed
-                        }
-                        else if (! IGNORE_INVALID_ENTRIES)
-                        {
-                            throw new IllegalArgumentException ("path entry is not a directory or an archive: [" + f + "]");
-                        }
-                    }
-                }
-            }
-            
-            PathEnumerator (final File [] path, final boolean canonical, final IPathHandler handler)
-            {
-                m_path = new ArrayList (path.length);
-                for (int p = 0; p < path.length; ++ p) m_path.add (path [p]);
-                
-                m_canonical = canonical;
-                
-                if (handler == null) throw new IllegalArgumentException ("null input: handler");
-                m_handler = handler;
-                
-                m_processManifest = true; // TODO
-                
-                if (m_processManifest)
-                {
-                    m_pathSet = new HashSet (path.length);
-                    for (int p = 0; p < path.length; ++ p)
-                    {
-                        m_pathSet.add (path [p].getPath ()); // set of [possibly canonical] paths
-                    }
-                }
-                else
-                {
-                    m_pathSet = null;
-                }
-                
-                m_log = Logger.getLogger (); // each path enumerator caches its logger at creation time
-                m_verbose = m_log.atVERBOSE ();
-                m_trace1 = m_log.atTRACE1 ();
-            }
-            
-            
-            private void enumeratePathDir (final String dir)
-                throws IOException
-            {
-                final boolean trace1 = m_trace1;
-                
-                final File currentPathDir = m_currentPathDir;
-                final File fullDir = dir != null ? new File (currentPathDir, dir) : currentPathDir;
-                
-                final String [] children = fullDir.list ();
-                final IPathHandler handler = m_handler;
-                
-                for (int c = 0, cLimit = children.length; c < cLimit; ++ c)
-                {
-                    final String childName = children [c];
-                    
-                    final File child = dir != null ? new File (dir, childName) : new File (childName);
-                    final File fullChild = new File (fullDir, childName);
-                    
-                    if (fullChild.isDirectory ())
-                    {
-                        handler.handleDirStart (currentPathDir, child);
-                        if (trace1) m_log.trace1 ("enumeratePathDir", "recursing into [" + child.getName () + "] ...");
-                        enumeratePathDir (child.getPath ());
-                        handler.handleDirEnd (currentPathDir, child);
-                    }
-                    else
-                    {
-//                        final String lcName = childName.toLowerCase ();
-//                        
-//                        if (lcName.endsWith (".zip") || lcName.endsWith (".jar"))
-//                        {
-//                            handler.handleArchiveStart (currentPathDir, child);
-//                            enumeratePathArchive (child.getPath ());
-//                            handler.handleArchiveEnd (currentPathDir, child);
-//                        }
-//                        else
-                        {
-                            if (trace1) m_log.trace1 ("enumeratePathDir", "processing file [" + child.getName () + "] ...");
-                            handler.handleFile (currentPathDir, child);
-                        }
-                    }
-                }
-            }
-            
-            private void enumeratePathArchive (final String archive)
-                throws IOException
-            {
-                final boolean trace1 = m_trace1;
-                
-                final File fullArchive = new File (m_currentPathDir, archive);
-                
-                JarInputStream in = null;
-                try
-                {
-                    // note: Sun's JarFile uses native code and has been known to 
-                    // crash the JVM in some builds; however, it uses random file
-                    // access and can find "bad" manifests that are not the first
-                    // entries in their archives (which JarInputStream can't do);
-                    // [bugs: 4263225, 4696354, 4338238]
-                    //
-                    // there is really no good solution here but as a compromise
-                    // I try to read the manifest again via a JarFile if the stream
-                    // returns null for it:
-                    
-                    in = new JarInputStream (new BufferedInputStream (new FileInputStream (fullArchive), 32 * 1024));
-                    
-                    final IPathHandler handler = m_handler;
-                    
-                    Manifest manifest = in.getManifest (); // can be null
-                    if (manifest == null) manifest = readManifestViaJarFile (fullArchive); // can be null 
-                    
-                    handler.handleArchiveStart (m_currentPathDir, new File (archive), manifest);
-                    
-                    // note: this loop does not skip over the manifest-related
-                    // entries [the handler needs to be smart about that]
-                    for (ZipEntry entry; (entry = in.getNextEntry ()) != null; )
-                    {
-                        // TODO: handle nested archives
-                        
-                        if (trace1) m_log.trace1 ("enumeratePathArchive", "processing archive entry [" + entry.getName () + "] ...");
-                        handler.handleArchiveEntry (in, entry);
-                        in.closeEntry ();
-                    }
-                    
-                    
-                    // TODO: this needs major testing
-                    if (m_processManifest)
-                    {
-                        // note: JarInputStream only reads the manifest if it the
-                        // first jar entry
-                        if (manifest == null) manifest = in.getManifest ();
-                        if (manifest != null)
-                        {
-                            final Attributes attributes = manifest.getMainAttributes ();
-                            if (attributes != null)
-                            {
-                                // note: Sun's documentation says that multiple Class-Path:
-                                // entries are merged sequentially (http://java.sun.com/products/jdk/1.2/docs/guide/extensions/spec.html)
-                                // however, their own code does not implement this 
-                                final String jarClassPath = attributes.getValue (Attributes.Name.CLASS_PATH);
-                                if (jarClassPath != null)
-                                {
-                                    final StringTokenizer tokenizer = new StringTokenizer (jarClassPath);
-                                    for (int p = 1; tokenizer.hasMoreTokens (); )
-                                    {
-                                        final String relPath = tokenizer.nextToken ();
-                                        
-                                        final File archiveParent = fullArchive.getParentFile ();
-                                        final File path = archiveParent != null ? new File (archiveParent, relPath) : new File (relPath);
-                                        
-                                        final String fullPath = m_canonical ? Files.canonicalizePathname (path.getPath ()) : path.getPath ();
-                                        
-                                        if (m_pathSet.add (fullPath))
-                                        {
-                                            if (m_verbose) m_log.verbose ("  added manifest Class-Path entry [" + path + "]");
-                                            m_path.add (m_pathIndex + (p ++), path); // insert after the current m_path entry
-                                        }
-                                    }
-                                }
-                            }
-                        }
-                    }
-                }
-                catch (FileNotFoundException fnfe) // ignore: this should not happen
-                {
-                    if ($assert.ENABLED) throw fnfe;
-                }
-                finally
-                {
-                    if (in != null) try { in.close (); } catch (Exception ignore) {}
-                }
-            }
-            
-            
-            // see comments at the start of enumeratePathArchive()
-            
-            private static Manifest readManifestViaJarFile (final File archive)
-            {
-                Manifest result = null;
-                
-                JarFile jarfile = null;
-                try
-                {
-                    jarfile = new JarFile (archive, false); // 3-arg constructor is not in J2SE 1.2
-                    result = jarfile.getManifest ();
-                }
-                catch (IOException ignore)
-                {
-                }
-                finally
-                {
-                    if (jarfile != null) try { jarfile.close (); } catch (IOException ignore) {} 
-                }
-                
-                return result;
-            } 
-            
-
-            private final ArrayList /* File */ m_path;
-            private final boolean m_canonical;
-            private final Set /* String */ m_pathSet;
-            private final IPathHandler m_handler;
-            private final boolean m_processManifest;
-            
-            private final Logger m_log;
-            private boolean m_verbose, m_trace1;
-            
-            private int m_pathIndex;
-            private File m_currentPathDir;
-            
-            // if 'true', non-existent or non-archive or non-directory path entries
-            // will be silently ignored: 
-            private static final boolean IGNORE_INVALID_ENTRIES = true; // this is consistent with the normal JVM behavior
-                        
-        } // end of nested class
-        
-    } // end of nested class
-        
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/IProperties.java b/core/java12/com/vladium/util/IProperties.java
deleted file mode 100644
index 09bb84e..0000000
--- a/core/java12/com/vladium/util/IProperties.java
+++ /dev/null
@@ -1,370 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IProperties.java,v 1.1.1.1.2.1 2004/07/08 10:52:10 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.PrintStream;
-import java.io.PrintWriter;
-import java.util.ArrayList;
-import java.util.Enumeration;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Properties;
-import java.util.Set;
-import java.util.TreeSet;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IProperties
-{
-    // public: ................................................................
-    
-    /**
-     * An IMapper is a stateless hook for mapping a arbitrary property key
-     * to another (useful, for example, for property aliasing and defaulting).
-     * Each IMapper must be completely stateless and could be shared between
-     * multiple IProperties instances (and invoked from multiple concurrent threads).
-     */
-    interface IMapper
-    {
-        String getMappedKey (final String key);
-        
-    } // end of nested interface
-    
-    
-    String getProperty (String key);
-    String getProperty (String key, String dflt);
-    boolean isOverridden (String key);
-    
-    IProperties copy ();
-    Iterator /* String */ properties ();
-    Properties toProperties ();
-    /**
-     * @param prefix [may not be null]
-     */
-    String [] toAppArgsForm (final String prefix);
-    boolean isEmpty ();
-    void list (PrintStream out);
-    void list (PrintWriter out);
-
-    String setProperty (String key, String value);
-    
-    
-    abstract class Factory
-    {
-        /**
-         * Creates an empty IProperties set with an optional property mapper.
-         * 
-         * @param mapper [may be null]
-         * @return an empty property set [never null]
-         */
-        public static IProperties create (final IMapper mapper)
-        {
-            return new PropertiesImpl (null, mapper);
-        }
-        
-        /**
-         * Converts a java.util.Properties instance to an IProperties instance,
-         * with an optional property mapper. Note that 'properties' content is
-         * shallowly cloned, so the result can be mutated independently from
-         * the input.
-         * 
-         * @param properties [may not be null]
-         * @param mapper [may be null]
-         * @return a property set based on 'properties' [never null]
-         */
-        public static IProperties wrap (final Properties properties, final IMapper mapper)
-        {
-            final HashMap map = new HashMap ();
-            
-            // always use propertyNames() for traversing java.util.Properties:
-            
-            for (Enumeration names = properties.propertyNames (); names.hasMoreElements (); )
-            {
-                final String n = (String) names.nextElement ();
-                final String v = properties.getProperty (n);
-                
-                map.put (n, v);
-            }
-            
-            return new PropertiesImpl (map, mapper); // note: map is a defensive clone
-        }
-
-        /**
-         * Combines two property sets by creating a property set that chains 'overrides'
-         * to 'base' for property delegation. Note that 'overrides' are cloned
-         * defensively and so the result can be mutated independently of both inputs.
-         * 
-         * @param overrides [may be null]
-         * @param base [may be null]
-         * @return [never null; an empty property set with a null mapper is created
-         * if both inputs are null]
-         */
-        public static IProperties combine (final IProperties overrides, final IProperties base)
-        {
-            final IProperties result = overrides != null
-                ? overrides.copy ()
-                : create (null);
-            
-            // [assertion: result != null]
-
-            ((PropertiesImpl) result).getLastProperties ().setDelegate ((PropertiesImpl) base);
-            
-            return result;
-        }
-        
-        /*
-         * Not MT-safe
-         */
-        private static final class PropertiesImpl implements IProperties, Cloneable
-        {
-            // ACCESSORS (IProperties):
-            
-            public String getProperty (final String key)
-            {
-                return getProperty (key, null);
-            }
-            
-            public String getProperty (final String key, final String dflt)
-            {
-                String value = (String) m_valueMap.get (key);
-                
-                // first, try to delegate horizontally:
-                if ((value == null) && (m_mapper != null))
-                {
-                    final String mappedKey = m_mapper.getMappedKey (key);
-                    
-                    if (mappedKey != null)
-                        value = (String) m_valueMap.get (mappedKey); 
-                }
-                
-                // next, try to delegate vertically:
-                if ((value == null) && (m_delegate != null))
-                {
-                    value = m_delegate.getProperty (key, null); 
-                }
-                
-                return value != null ? value : dflt;
-            }
-            
-            public boolean isOverridden (final String key)
-            {
-                return m_valueMap.containsKey (key);
-            }
-            
-            public IProperties copy ()
-            {
-                final PropertiesImpl _clone;
-                try
-                {
-                    _clone = (PropertiesImpl) super.clone ();
-                }
-                catch (CloneNotSupportedException cnse)
-                {
-                    throw new Error (cnse.toString ()); // never happens
-                }
-
-                _clone.m_valueMap = (HashMap) m_valueMap.clone ();
-                _clone.m_unmappedKeySet = null;
-                
-                // note: m_mapper field is not cloned by design (mappers are stateless/shareable)
-                
-                PropertiesImpl scan = _clone;
-                for (PropertiesImpl delegate = m_delegate; delegate != null; delegate = delegate.m_delegate)
-                {
-                    final PropertiesImpl _delegateClone;
-                    try
-                    {
-                        _delegateClone = (PropertiesImpl) delegate.clone ();
-                    }
-                    catch (CloneNotSupportedException cnse)
-                    {
-                        throw new Error (cnse.toString ()); // never happens
-                    }
-                    
-                    // note that the value map needs to be cloned not only for the
-                    // outermost IProperties set but for the inner ones as well
-                    // (to prevent independent mutation in them from showing through)
-                    
-                    _delegateClone.m_valueMap = (HashMap) delegate.m_valueMap.clone ();
-                    _delegateClone.m_unmappedKeySet = null; // ensure that the last delegate will have this field reset
-                    
-                    scan.setDelegate (_delegateClone);
-                    scan = _delegateClone;
-                }
-                
-                return _clone;
-            }
-            
-            public Iterator /* String */ properties ()
-            {
-                return unmappedKeySet ().iterator ();
-            }
-            
-            public Properties toProperties ()
-            {
-                final Properties result = new Properties ();
-                
-                for (Iterator i = properties (); i.hasNext (); )
-                {
-                    final String n = (String) i.next ();
-                    final String v = getProperty (n);
-                    
-                    result.setProperty (n, v);
-                }
-                
-                return result;
-            }
-            
-            public boolean isEmpty ()
-            {
-                return m_valueMap.isEmpty () && ((m_delegate == null) || ((m_delegate != null) && m_delegate.isEmpty ()));
-            }
-            
-            public String [] toAppArgsForm (final String prefix)
-            {
-                if (isEmpty ())
-                    return IConstants.EMPTY_STRING_ARRAY;
-                else
-                {
-                    if (prefix == null)
-                        throw new IllegalArgumentException ("null input: prefix");
-                    
-                    final List _result = new ArrayList ();
-                    for (Iterator names = properties (); names.hasNext (); )
-                    {
-                        final String name = (String) names.next ();
-                        final String value = getProperty (name, "");
-                        
-                        _result.add (prefix.concat (name).concat ("=").concat (value)); 
-                    }
-                    
-                    final String [] result = new String [_result.size ()];
-                    _result.toArray (result);
-                    
-                    return result;
-                }
-            }    
-
-            public void list (final PrintStream out)
-            {
-                if (out != null)
-                {
-                    for (Iterator i = properties (); i.hasNext (); )
-                    {
-                        final String n = (String) i.next ();
-                        final String v = getProperty (n);
-                        
-                        out.println (n + ":\t[" + v + "]");
-                    }
-                }
-            }
-            
-            public void list (final PrintWriter out)
-            {
-                if (out != null)
-                {
-                    for (Iterator i = properties (); i.hasNext (); )
-                    {
-                        final String n = (String) i.next ();
-                        final String v = getProperty (n);
-                        
-                        out.println (n + ":\t[" + v + "]");
-                    }
-                }
-            }
-            
-            // MUTATORS:
-            
-            public String setProperty (final String key, final String value)
-            {
-                if (value == null)
-                    throw new IllegalArgumentException ("null input: value");
-                
-                m_unmappedKeySet = null;
-                
-                return (String) m_valueMap.put (key, value); 
-            }
-            
-            
-            PropertiesImpl (final HashMap values, final IMapper mapper)
-            {
-                m_mapper = mapper;
-                m_valueMap = values != null ? values : new HashMap ();
-                
-                m_delegate = null;
-            }
-            
-            
-            Set unmappedKeySet ()
-            {
-                Set result = m_unmappedKeySet;
-                if (result == null)
-                {
-                    result = new TreeSet ();
-                    result.addAll (m_valueMap.keySet ());
-                    if (m_delegate != null)
-                        result.addAll (m_delegate.unmappedKeySet ());
-                    
-                    m_unmappedKeySet = result;
-                    return result;
-                }
-                
-                return result;
-            }
-            
-            // ACCESSORS:
-            
-            PropertiesImpl getLastProperties ()
-            {
-                PropertiesImpl result = this;
-                
-                for (PropertiesImpl delegate = m_delegate; delegate != null; delegate = delegate.m_delegate)
-                {
-                    // this does not detect all possible cycles:
-                    if (delegate == this)
-                        throw new IllegalStateException ("cyclic delegation detected");
-                    
-                    result = delegate;
-                }
-                
-                return result;
-            }
-            
-            // MUTATORS:
-            
-            void setDelegate (final PropertiesImpl delegate)
-            {
-                m_delegate = delegate;
-                
-                m_unmappedKeySet = null;
-            }
-            
-            
-            private final IMapper m_mapper;
-            private /*final*/ HashMap m_valueMap; // never null
-            
-            private PropertiesImpl m_delegate;
-            private transient Set m_unmappedKeySet;
-            
-        } // end of nested class
-        
-    } // end of nested class
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/IntIntMap.java b/core/java12/com/vladium/util/IntIntMap.java
deleted file mode 100644
index 7abe824..0000000
--- a/core/java12/com/vladium/util/IntIntMap.java
+++ /dev/null
@@ -1,330 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IntIntMap.java,v 1.1.1.1 2004/05/09 16:57:53 vlad_r Exp $
- */
-package com.vladium.util;
-
-// ----------------------------------------------------------------------------
-/**
- *
- * MT-safety: an instance of this class is <I>not</I> safe for access from
- * multiple concurrent threads [even if access is done by a single thread at a
- * time]. The caller is expected to synchronize externally on an instance [the
- * implementation does not do internal synchronization for the sake of efficiency].
- * java.util.ConcurrentModificationException is not supported either.
- *
- * @author Vlad Roubtsov, (C) 2001
- */
-public
-final class IntIntMap
-{
-    // public: ................................................................
-    
-    // TODO: optimize key comparisons using key.hash == entry.key.hash condition
-
-    /**
-     * Equivalent to <CODE>IntObjectMap(11, 0.75F)</CODE>.
-     */
-    public IntIntMap ()
-    {
-        this (11, 0.75F);
-    }
-    
-    /**
-     * Equivalent to <CODE>IntObjectMap(capacity, 0.75F)</CODE>.
-     */
-    public IntIntMap (final int initialCapacity)
-    {
-        this (initialCapacity, 0.75F);
-    }
-    
-    /**
-     * Constructs an IntObjectMap with specified initial capacity and load factor.
-     *
-     * @param initialCapacity initial number of hash buckets in the table [may not be negative, 0 is equivalent to 1].
-     * @param loadFactor the load factor to use to determine rehashing points [must be in (0.0, 1.0] range].
-     */
-    public IntIntMap (int initialCapacity, final float loadFactor)
-    {
-        if (initialCapacity < 0) throw new IllegalArgumentException ("negative input: initialCapacity [" + initialCapacity + "]");
-        if ((loadFactor <= 0.0) || (loadFactor >= 1.0 + 1.0E-6))
-            throw new IllegalArgumentException ("loadFactor not in (0.0, 1.0] range: " + loadFactor);
-        
-        if (initialCapacity == 0) initialCapacity = 1;
-        
-        m_loadFactor = loadFactor > 1.0 ? 1.0F : loadFactor;        
-        m_sizeThreshold = (int) (initialCapacity * loadFactor);
-        m_buckets = new Entry [initialCapacity];
-    }
-    
-    
-    /**
-     * Overrides Object.toString() for debug purposes.
-     */
-    public String toString ()
-    {
-        final StringBuffer s = new StringBuffer ();
-        debugDump (s);
-        
-        return s.toString ();
-    }
-    
-    /**
-     * Returns the number of key-value mappings in this map.
-     */
-    public int size ()
-    {
-        return m_size;
-    }
-
-    public boolean contains (final int key)
-    {
-        // index into the corresponding hash bucket:
-        final Entry [] buckets = m_buckets;
-        final int bucketIndex = (key & 0x7FFFFFFF) % buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if (key == entry.m_key) return true;
-        }
-        
-        return false;
-    }
-    
-    /**
-     * Returns the value that is mapped to a given 'key'. Returns
-     * false if this key has never been mapped.
-     *
-     * @param key mapping key
-     * @param out holder for the found value [must be at least of size 1]
-     *
-     * @return 'true' if this key was mapped to an existing value
-     */
-    public boolean get (final int key, final int [] out)
-    {
-        // index into the corresponding hash bucket:
-        final Entry [] buckets = m_buckets;
-        final int bucketIndex = (key & 0x7FFFFFFF) % buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if (key == entry.m_key)
-            {
-                out [0] = entry.m_value;
-                return true;
-            }
-        }
-        
-        return false;
-    }
-    
-    public boolean get (final int key, final int [] out, final int index)
-    {
-        // index into the corresponding hash bucket:
-        final Entry [] buckets = m_buckets;
-        final int bucketIndex = (key & 0x7FFFFFFF) % buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if (key == entry.m_key)
-            {
-                out [index] = entry.m_value;
-                return true;
-            }
-        }
-        
-        return false;
-    }
-    
-    public int [] keys ()
-    {
-        final int [] result = new int [m_size];
-        int scan = 0;
-        
-        for (int b = 0; b < m_buckets.length; ++ b)
-        {
-            for (Entry entry = m_buckets [b]; entry != null; entry = entry.m_next)
-            {
-                result [scan ++] = entry.m_key;
-            }
-        }
-        
-        return result;
-    }
-    
-    /**
-     * Updates the table to map 'key' to 'value'. Any existing mapping is overwritten.
-     *
-     * @param key mapping key
-     * @param value mapping value
-     */
-    public void put (final int key, final int value)
-    {
-        Entry currentKeyEntry = null;
-        
-        // detect if 'key' is already in the table [in which case, set 'currentKeyEntry' to point to its entry]:
-        
-        // index into the corresponding hash bucket:
-        int bucketIndex = (key & 0x7FFFFFFF) % m_buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        Entry [] buckets = m_buckets;
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if (key == entry.m_key)
-            {
-                currentKeyEntry = entry;
-                break;
-            }
-        }
-        
-        if (currentKeyEntry != null)
-        {
-            // replace the current value:
-                
-            currentKeyEntry.m_value = value;
-        }
-        else
-        {
-            // add a new entry:
-            
-            if (m_size >= m_sizeThreshold) rehash ();
-            
-            buckets = m_buckets;
-            bucketIndex = (key & 0x7FFFFFFF) % buckets.length;
-            final Entry bucketListHead = buckets [bucketIndex];
-            final Entry newEntry = new Entry (key, value, bucketListHead);
-            buckets [bucketIndex] = newEntry;
-            
-            ++ m_size;
-        }
-    }
-    
-    /**
-     * Updates the table to map 'key' to 'value'. Any existing mapping is overwritten.
-     *
-     * @param key mapping key
-     */
-    public void remove (final int key)
-    {
-        // index into the corresponding hash bucket:
-        final int bucketIndex = (key  & 0x7FFFFFFF) % m_buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        Entry [] buckets = m_buckets;
-        for (Entry entry = buckets [bucketIndex], prev = entry; entry != null; )
-        {
-            final Entry next = entry.m_next;
-            
-            if (key == entry.m_key)
-            {
-                if (prev == entry)
-                    buckets [bucketIndex] = next;
-                else
-                    prev.m_next = next;
-                
-                -- m_size;     
-                break;
-            }
-            
-            prev = entry;
-            entry = next;
-        }
-    }
-
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    void debugDump (final StringBuffer out)
-    {
-        if (out != null)
-        {
-            out.append (super.toString ()); out.append (EOL);
-            out.append ("size = " + m_size + ", bucket table size = " + m_buckets.length + ", load factor = " + m_loadFactor + EOL);
-            out.append ("size threshold = " + m_sizeThreshold + EOL);
-        }
-    }
-
-    // private: ...............................................................
-
-    
-    /**
-     * The structure used for chaining colliding keys.
-     */
-    private static final class Entry
-    {
-        Entry (final int key, final int value, final Entry next)
-        {
-            m_key = key; 
-            m_value = value;
-            m_next = next;
-        }
-        
-        int m_key;
-        int m_value;
-        
-        Entry m_next; // singly-linked list link
-        
-    } // end of nested class
-    
-
-    /**
-     * Re-hashes the table into a new array of buckets.
-     */
-    private void rehash ()
-    {
-        // TODO: it is possible to run this method twice, first time using the 2*k+1 prime sequencer for newBucketCount
-        // and then with that value reduced to actually shrink capacity. As it is right now, the bucket table can
-        // only grow in size
-        
-        final Entry [] buckets = m_buckets;
-        
-        final int newBucketCount = (m_buckets.length << 1) + 1;
-        final Entry [] newBuckets = new Entry [newBucketCount];
-
-        // rehash all entry chains in every bucket:
-        for (int b = 0; b < buckets.length; ++ b)
-        {
-            for (Entry entry = buckets [b]; entry != null; )
-            {
-                final Entry next = entry.m_next; // remember next pointer because we are going to reuse this entry
-                final int entryKeyHash = entry.m_key & 0x7FFFFFFF;
-            
-                // index into the corresponding new hash bucket:
-                final int newBucketIndex = entryKeyHash % newBucketCount;
-                
-                final Entry bucketListHead = newBuckets [newBucketIndex];
-                entry.m_next = bucketListHead;
-                newBuckets [newBucketIndex] = entry;                                
-                
-                entry = next;
-            }
-        }
-        
-
-        m_sizeThreshold = (int) (newBucketCount * m_loadFactor);
-        m_buckets = newBuckets;
-    }
-    
-    
-    private final float m_loadFactor; // determines the setting of m_sizeThreshold
-    
-    private Entry [] m_buckets; // table of buckets
-    private int m_size; // number of keys in the table, not cleared as of last check
-    private int m_sizeThreshold; // size threshold for rehashing
-        
-    private static final String EOL = System.getProperty ("line.separator", "\n");
-    
-} // end of class
-// ----------------------------------------------------------------------------
-
diff --git a/core/java12/com/vladium/util/IntObjectMap.java b/core/java12/com/vladium/util/IntObjectMap.java
deleted file mode 100644
index 6cc6e70..0000000
--- a/core/java12/com/vladium/util/IntObjectMap.java
+++ /dev/null
@@ -1,288 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IntObjectMap.java,v 1.1.1.1 2004/05/09 16:57:53 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.Serializable;
-
-// ----------------------------------------------------------------------------
-/**
- *
- * MT-safety: an instance of this class is <I>not</I> safe for access from
- * multiple concurrent threads [even if access is done by a single thread at a
- * time]. The caller is expected to synchronize externally on an instance [the
- * implementation does not do internal synchronization for the sake of efficiency].
- * java.util.ConcurrentModificationException is not supported either.
- *
- * @author Vlad Roubtsov, (C) 2001
- */
-public
-final class IntObjectMap implements Serializable
-{
-    // public: ................................................................
-
-    /**
-     * Equivalent to <CODE>IntObjectMap(11, 0.75F)</CODE>.
-     */
-    public IntObjectMap ()
-    {
-        this (11, 0.75F);
-    }
-    
-    /**
-     * Equivalent to <CODE>IntObjectMap(capacity, 0.75F)</CODE>.
-     */
-    public IntObjectMap (final int initialCapacity)
-    {
-        this (initialCapacity, 0.75F);
-    }
-    
-    /**
-     * Constructs an IntObjectMap with specified initial capacity and load factor.
-     *
-     * @param initialCapacity initial number of hash buckets in the table [may not be negative, 0 is equivalent to 1].
-     * @param loadFactor the load factor to use to determine rehashing points [must be in (0.0, 1.0] range].
-     */
-    public IntObjectMap (int initialCapacity, final float loadFactor)
-    {
-        if (initialCapacity < 0) throw new IllegalArgumentException ("negative input: initialCapacity [" + initialCapacity + "]");
-        if ((loadFactor <= 0.0) || (loadFactor >= 1.0 + 1.0E-6))
-            throw new IllegalArgumentException ("loadFactor not in (0.0, 1.0] range: " + loadFactor);
-        
-        if (initialCapacity == 0) initialCapacity = 1;
-        
-        m_loadFactor = loadFactor > 1.0 ? 1.0F : loadFactor;        
-        m_sizeThreshold = (int) (initialCapacity * loadFactor);
-        m_buckets = new Entry [initialCapacity];
-    }
-    
-    
-    /**
-     * Overrides Object.toString() for debug purposes.
-     */
-    public String toString ()
-    {
-        final StringBuffer s = new StringBuffer ();
-        debugDump (s);
-        
-        return s.toString ();
-    }
-    
-    /**
-     * Returns the number of key-value mappings in this map.
-     */
-    public int size ()
-    {
-        return m_size;
-    }
-
-    public boolean contains (final int key)
-    {
-        // index into the corresponding hash bucket:
-        final Entry [] buckets = m_buckets;
-        final int bucketIndex = (key & 0x7FFFFFFF) % buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if (key == entry.m_key)
-                return true;
-        }
-        
-        return false;
-    }
-    
-    /**
-     * Returns the value that is mapped to a given 'key'. Returns
-     * null if (a) this key has never been mapped or (b) it has been
-     * mapped to a null value.
-     *
-     * @param key mapping key
-     *
-     * @return Object value mapping for 'key' [can be null].
-     */
-    public Object get (final int key)
-    {
-        // index into the corresponding hash bucket:
-        final Entry [] buckets = m_buckets;
-        final int bucketIndex = (key & 0x7FFFFFFF) % buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if (key == entry.m_key)
-                return entry.m_value;
-        }
-        
-        return null;
-    }
-    
-    public int [] keys ()
-    {
-        if (m_size == 0)
-            return IConstants.EMPTY_INT_ARRAY;
-        else
-        {
-            final int [] result = new int [m_size];
-            int scan = 0;
-            
-            for (int b = 0; b < m_buckets.length; ++ b)
-            {
-                for (Entry entry = m_buckets [b]; entry != null; entry = entry.m_next)
-                {
-                    result [scan ++] = entry.m_key;
-                }
-            }
-            
-            return result;
-        }
-    }
-    
-    /**
-     * Updates the table to map 'key' to 'value'. Any existing mapping is overwritten.
-     *
-     * @param key mapping key
-     * @param value mapping value [can be null].
-     *
-     * @return Object previous value mapping for 'key' [can be null]
-     */
-    public Object put (final int key, final Object value)
-    {
-        Entry currentKeyEntry = null;
-        
-        // detect if 'key' is already in the table [in which case, set 'currentKeyEntry' to point to its entry]:
-        
-        // index into the corresponding hash bucket:
-        int bucketIndex = (key & 0x7FFFFFFF) % m_buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        Entry [] buckets = m_buckets;
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if (key == entry.m_key)
-            {
-                currentKeyEntry = entry;
-                break;
-            }
-        }
-        
-        if (currentKeyEntry != null)
-        {
-            // replace the current value:
-                
-            final Object currentKeyValue = currentKeyEntry.m_value;
-            currentKeyEntry.m_value = value;
-            
-            return currentKeyValue;
-        }
-        else
-        {
-            // add a new entry:
-            
-            if (m_size >= m_sizeThreshold) rehash ();
-            
-            buckets = m_buckets;
-            bucketIndex = (key & 0x7FFFFFFF) % buckets.length;
-            final Entry bucketListHead = buckets [bucketIndex];
-            final Entry newEntry = new Entry (key, value, bucketListHead);
-            buckets [bucketIndex] = newEntry;
-            
-            ++ m_size;
-            
-            return null;
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    void debugDump (final StringBuffer out)
-    {
-        if (out != null)
-        {
-            out.append (super.toString ()); out.append (EOL);
-            out.append ("size = " + m_size + ", bucket table size = " + m_buckets.length + ", load factor = " + m_loadFactor + EOL);
-            out.append ("size threshold = " + m_sizeThreshold + EOL);
-        }
-    }
-
-    // private: ...............................................................
-
-    
-    /**
-     * The structure used for chaining colliding keys.
-     */
-    private static final class Entry implements Serializable
-    {
-        Entry (final int key, final Object value, final Entry next)
-        {
-            m_key = key; 
-            m_value = value;
-            m_next = next;
-        }
-        
-        Object m_value;           // reference to the value [never null]
-        final int m_key;
-        
-        Entry m_next; // singly-linked list link
-        
-    } // end of nested class
-    
-
-    /**
-     * Re-hashes the table into a new array of buckets.
-     */
-    private void rehash ()
-    {
-        // TODO: it is possible to run this method twice, first time using the 2*k+1 prime sequencer for newBucketCount
-        // and then with that value reduced to actually shrink capacity. As it is right now, the bucket table can
-        // only grow in size
-        
-        final Entry [] buckets = m_buckets;
-        
-        final int newBucketCount = (m_buckets.length << 1) + 1;
-        final Entry [] newBuckets = new Entry [newBucketCount];
-
-        // rehash all entry chains in every bucket:
-        for (int b = 0; b < buckets.length; ++ b)
-        {
-            for (Entry entry = buckets [b]; entry != null; )
-            {
-                final Entry next = entry.m_next; // remember next pointer because we are going to reuse this entry
-                final int entryKey = entry.m_key;
-            
-                // index into the corresponding new hash bucket:
-                final int newBucketIndex = (entryKey & 0x7FFFFFFF) % newBucketCount;
-                
-                final Entry bucketListHead = newBuckets [newBucketIndex];
-                entry.m_next = bucketListHead;
-                newBuckets [newBucketIndex] = entry;                                
-                
-                entry = next;
-            }
-        }
-        
-
-        m_sizeThreshold = (int) (newBucketCount * m_loadFactor);
-        m_buckets = newBuckets;
-    }
-    
-    
-    private final float m_loadFactor; // determines the setting of m_sizeThreshold
-    
-    private Entry [] m_buckets; // table of buckets
-    private int m_size; // number of keys in the table, not cleared as of last check
-    private int m_sizeThreshold; // size threshold for rehashing
-        
-    private static final String EOL = System.getProperty ("line.separator", "\n");
-    
-} // end of class
-// ----------------------------------------------------------------------------
-
diff --git a/core/java12/com/vladium/util/IntSet.java b/core/java12/com/vladium/util/IntSet.java
deleted file mode 100644
index 8cf2d99..0000000
--- a/core/java12/com/vladium/util/IntSet.java
+++ /dev/null
@@ -1,260 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IntSet.java,v 1.1.1.1 2004/05/09 16:57:53 vlad_r Exp $
- */
-package com.vladium.util;
-
-// ----------------------------------------------------------------------------
-/**
- *
- * MT-safety: an instance of this class is <I>not</I> safe for access from
- * multiple concurrent threads [even if access is done by a single thread at a
- * time]. The caller is expected to synchronize externally on an instance [the
- * implementation does not do internal synchronization for the sake of efficiency].
- * java.util.ConcurrentModificationException is not supported either.
- *
- * @author Vlad Roubtsov, (C) 2001
- */
-public
-final class IntSet
-{
-    // public: ................................................................
-
-    /**
-     * Equivalent to <CODE>IntSet(11, 0.75F)</CODE>.
-     */
-    public IntSet ()
-    {
-        this (11, 0.75F);
-    }
-    
-    /**
-     * Equivalent to <CODE>IntSet(capacity, 0.75F)</CODE>.
-     */
-    public IntSet (final int initialCapacity)
-    {
-        this (initialCapacity, 0.75F);
-    }
-    
-    /**
-     * Constructs an IntSet with specified initial capacity and load factor.
-     *
-     * @param initialCapacity initial number of hash buckets in the table [may not be negative, 0 is equivalent to 1].
-     * @param loadFactor the load factor to use to determine rehashing points [must be in (0.0, 1.0] range].
-     */
-    public IntSet (int initialCapacity, final float loadFactor)
-    {
-        if (initialCapacity < 0) throw new IllegalArgumentException ("negative input: initialCapacity [" + initialCapacity + "]");
-        if ((loadFactor <= 0.0) || (loadFactor >= 1.0 + 1.0E-6))
-            throw new IllegalArgumentException ("loadFactor not in (0.0, 1.0] range: " + loadFactor);
-        
-        if (initialCapacity == 0) initialCapacity = 1;
-        
-        m_loadFactor = loadFactor > 1.0 ? 1.0F : loadFactor;        
-        m_sizeThreshold = (int) (initialCapacity * loadFactor);
-        m_buckets = new Entry [initialCapacity];
-    }
-    
-    
-    /**
-     * Overrides Object.toString() for debug purposes.
-     */
-    public String toString ()
-    {
-        final StringBuffer s = new StringBuffer ();
-        debugDump (s);
-        
-        return s.toString ();
-    }
-    
-    /**
-     * Returns the number of key-value mappings in this map.
-     */
-    public int size ()
-    {
-        return m_size;
-    }
-    
-    public boolean contains (final int key)
-    {
-        // index into the corresponding hash bucket:
-        final Entry [] buckets = m_buckets;
-        final int bucketIndex = (key & 0x7FFFFFFF) % buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if (key == entry.m_key)
-                return true;
-        }
-        
-        return false;
-    }
-    
-    public int [] values ()
-    {
-        if (m_size == 0)
-            return IConstants.EMPTY_INT_ARRAY;
-        else
-        {
-            final int [] result = new int [m_size];
-            int scan = 0;
-            
-            for (int b = 0; b < m_buckets.length; ++ b)
-            {
-                for (Entry entry = m_buckets [b]; entry != null; entry = entry.m_next)
-                {
-                    result [scan ++] = entry.m_key;
-                }
-            }
-            
-            return result;
-        }
-    }
-    
-    public void values (final int [] target, final int offset)
-    {
-        if (m_size != 0)
-        {
-            int scan = offset;
-            
-            for (int b = 0; b < m_buckets.length; ++ b)
-            {
-                for (Entry entry = m_buckets [b]; entry != null; entry = entry.m_next)
-                {
-                    target [scan ++] = entry.m_key;
-                }
-            }
-        }
-    }
-    
-    public boolean add (final int key)
-    {
-        Entry currentKeyEntry = null;
-        
-        // detect if 'key' is already in the table [in which case, set 'currentKeyEntry' to point to its entry]:
-        
-        // index into the corresponding hash bucket:
-        int bucketIndex = (key & 0x7FFFFFFF) % m_buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        Entry [] buckets = m_buckets;
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if (key == entry.m_key)
-            {
-                currentKeyEntry = entry;
-                break;
-            }
-        }
-        
-        if (currentKeyEntry == null)
-        {
-            // add a new entry:
-            
-            if (m_size >= m_sizeThreshold) rehash ();
-            
-            buckets = m_buckets;
-            bucketIndex = (key & 0x7FFFFFFF) % buckets.length;
-            final Entry bucketListHead = buckets [bucketIndex];
-            final Entry newEntry = new Entry (key, bucketListHead);
-            buckets [bucketIndex] = newEntry;
-            
-            ++ m_size;
-            
-            return true;
-        }
-        else
-            return false;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    void debugDump (final StringBuffer out)
-    {
-        if (out != null)
-        {
-            out.append (super.toString ()); out.append (EOL);
-            out.append ("size = " + m_size + ", bucket table size = " + m_buckets.length + ", load factor = " + m_loadFactor + EOL);
-            out.append ("size threshold = " + m_sizeThreshold + EOL);
-        }
-    }
-
-    // private: ...............................................................
-
-    
-    /**
-     * The structure used for chaining colliding keys.
-     */
-    private static final class Entry
-    {
-        Entry (final int key, final Entry next)
-        {
-            m_key = key; 
-            m_next = next;
-        }
-        
-        final int m_key;
-        
-        Entry m_next; // singly-linked list link
-        
-    } // end of nested class
-    
-
-    /**
-     * Re-hashes the table into a new array of buckets.
-     */
-    private void rehash ()
-    {
-        // TODO: it is possible to run this method twice, first time using the 2*k+1 prime sequencer for newBucketCount
-        // and then with that value reduced to actually shrink capacity. As it is right now, the bucket table can
-        // only grow in size
-        
-        final Entry [] buckets = m_buckets;
-        
-        final int newBucketCount = (m_buckets.length << 1) + 1;
-        final Entry [] newBuckets = new Entry [newBucketCount];
-
-        // rehash all entry chains in every bucket:
-        for (int b = 0; b < buckets.length; ++ b)
-        {
-            for (Entry entry = buckets [b]; entry != null; )
-            {
-                final Entry next = entry.m_next; // remember next pointer because we are going to reuse this entry
-                final int entryKey = entry.m_key;
-            
-                // index into the corresponding new hash bucket:
-                final int newBucketIndex = (entryKey & 0x7FFFFFFF) % newBucketCount;
-                
-                final Entry bucketListHead = newBuckets [newBucketIndex];
-                entry.m_next = bucketListHead;
-                newBuckets [newBucketIndex] = entry;                                
-                
-                entry = next;
-            }
-        }
-        
-
-        m_sizeThreshold = (int) (newBucketCount * m_loadFactor);
-        m_buckets = newBuckets;
-    }
-    
-    
-    private final float m_loadFactor; // determines the setting of m_sizeThreshold
-    
-    private Entry [] m_buckets; // table of buckets
-    private int m_size; // number of keys in the table, not cleared as of last check
-    private int m_sizeThreshold; // size threshold for rehashing
-        
-    private static final String EOL = System.getProperty ("line.separator", "\n");
-    
-} // end of class
-// ----------------------------------------------------------------------------
-
diff --git a/core/java12/com/vladium/util/IntVector.java b/core/java12/com/vladium/util/IntVector.java
deleted file mode 100644
index 3e159be..0000000
--- a/core/java12/com/vladium/util/IntVector.java
+++ /dev/null
@@ -1,157 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IntVector.java,v 1.1.1.1 2004/05/09 16:57:53 vlad_r Exp $
- */
-package com.vladium.util;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2001
- */
-public
-final class IntVector implements Cloneable
-{
-    // public: ................................................................
-    
-    public IntVector ()
-    {
-        this (5);
-    }
-    
-    public IntVector (final int initCapacity)
-    {
-        m_values = new int [initCapacity];
-    }
-    
-    // ACCESSORS:
-    
-    public int get (final int index)
-    {
-        if (index > m_size - 1)
-            throw new IndexOutOfBoundsException ("get[" + index + "] on vector of size " + m_size);
-                
-        return m_values [index];
-    }
-    
-    public int [] values ()
-    {
-        if (m_size == 0)
-            return IConstants.EMPTY_INT_ARRAY;
-        else
-        {
-            final int size = m_size;
-            final int [] result = new int [size];
-            
-            if (size < COPY_THRESHOLD)
-            {
-                for (int i = 0; i < size; ++ i) result [i] = m_values [i];
-            }
-            else
-            {
-                System.arraycopy (m_values, 0, result, 0, size);
-            }
-            
-            return result;
-        }
-    }
-    
-    public int size ()
-    {
-        return m_size;
-    }
-    
-    // Cloneable:
-    
-    /**
-     * Performs deep copy.
-     */
-    public Object clone ()
-    {
-        try
-        {
-            final IntVector _clone = (IntVector) super.clone ();
-            
-            // deep clone:
-            if (m_size < COPY_THRESHOLD)
-            {
-                _clone.m_values = new int [m_values.length];
-                final int [] _clone_values = _clone.m_values;
-                for (int i = 0; i < m_size; ++ i) _clone_values [i] = m_values [i];
-            }
-            else
-            {
-                _clone.m_values = (int []) m_values.clone ();
-            }
-            
-            return _clone;
-        }
-        catch (CloneNotSupportedException e)
-        {
-            throw new InternalError (e.toString ());
-        }
-    }
-    
-    public String toString ()
-    {
-        final StringBuffer s = new StringBuffer (super.toString() + ", size " + m_size + ": ");
-        for (int i = 0; i < m_size; ++ i)
-        {
-            if (i > 0) s.append (", ");
-            s.append (m_values [i]);
-        }
-        
-        return s.toString ();
-    }
-    
-    // MUTATORS:
-    
-    public int set (final int index, final int value)
-    {
-        if (index > m_size - 1)
-            throw new IndexOutOfBoundsException ("get[" + index + "] on vector of size " + m_size);
-        
-        final int current_value = m_values [index];
-        m_values [index] = value;
-        
-        return current_value;
-    }
-    
-    public void add (final int value)
-    {
-        final int capacity = m_values.length;
-        if (capacity == m_size)
-        {
-            final int [] values = new int [1 + (capacity << 1)];
-            if (capacity < COPY_THRESHOLD)
-            {
-                for (int i = 0; i < capacity; ++ i) values [i] = m_values [i];
-            }
-            else
-            {
-                System.arraycopy (m_values, 0, values, 0, capacity);
-            }
-            
-            m_values = values;
-        }
-        
-        m_values [m_size ++] = value;
-    }    
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private int [] m_values; // never null
-    private int m_size;
-    
-    private static final int COPY_THRESHOLD = 10;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/IntegerFactory.java b/core/java12/com/vladium/util/IntegerFactory.java
deleted file mode 100644
index 5608672..0000000
--- a/core/java12/com/vladium/util/IntegerFactory.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IntegerFactory.java,v 1.1.1.1 2004/05/09 16:57:52 vlad_r Exp $
- */
-package com.vladium.util;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class IntegerFactory
-{
-    // public: ................................................................
-    
-    // TODO: use thread-local arena pattern to avoid synchronization ?
-    
-    public static Integer getInteger (final int value)
-    {
-        synchronized (s_values)
-        {
-            final Object _result = s_values.get (value);
-            
-            if (_result == null)
-            {
-                final Integer result = new Integer (value);
-                s_values.put (value, result);
-                
-                return result; 
-            }
-            
-            return (Integer) _result;
-        }
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private IntegerFactory () {} // prevent subclassing
-    
-    
-    private static final IntObjectMap s_values = new IntObjectMap (16661);
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/ObjectIntMap.java b/core/java12/com/vladium/util/ObjectIntMap.java
deleted file mode 100644
index 28eb3a0..0000000
--- a/core/java12/com/vladium/util/ObjectIntMap.java
+++ /dev/null
@@ -1,326 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ObjectIntMap.java,v 1.1.1.1 2004/05/09 16:57:54 vlad_r Exp $
- */
-package com.vladium.util;
-
-import com.vladium.util.asserts.$assert;
-
-// ----------------------------------------------------------------------------
-/**
- *
- * MT-safety: an instance of this class is <I>not</I> safe for access from
- * multiple concurrent threads [even if access is done by a single thread at a
- * time]. The caller is expected to synchronize externally on an instance [the
- * implementation does not do internal synchronization for the sake of efficiency].
- * java.util.ConcurrentModificationException is not supported either.
- *
- * @author (C) 2001, Vlad Roubtsov
- */
-public
-final class ObjectIntMap
-{
-    // public: ................................................................
-    
-    // TODO: optimize key comparisons using key.hash == entry.key.hash condition
-
-    /**
-     * Equivalent to <CODE>IntObjectMap(11, 0.75F)</CODE>.
-     */
-    public ObjectIntMap ()
-    {
-        this (11, 0.75F);
-    }
-    
-    /**
-     * Equivalent to <CODE>IntObjectMap(capacity, 0.75F)</CODE>.
-     */
-    public ObjectIntMap (final int initialCapacity)
-    {
-        this (initialCapacity, 0.75F);
-    }
-    
-    /**
-     * Constructs an IntObjectMap with specified initial capacity and load factor.
-     *
-     * @param initialCapacity initial number of hash buckets in the table [may not be negative, 0 is equivalent to 1].
-     * @param loadFactor the load factor to use to determine rehashing points [must be in (0.0, 1.0] range].
-     */
-    public ObjectIntMap (int initialCapacity, final float loadFactor)
-    {
-        if (initialCapacity < 0) throw new IllegalArgumentException ("negative input: initialCapacity [" + initialCapacity + "]");
-        if ((loadFactor <= 0.0) || (loadFactor >= 1.0 + 1.0E-6))
-            throw new IllegalArgumentException ("loadFactor not in (0.0, 1.0] range: " + loadFactor);
-        
-        if (initialCapacity == 0) initialCapacity = 1;
-        
-        m_loadFactor = loadFactor > 1.0 ? 1.0F : loadFactor;        
-        m_sizeThreshold = (int) (initialCapacity * loadFactor);
-        m_buckets = new Entry [initialCapacity];
-    }
-    
-    
-    /**
-     * Overrides Object.toString() for debug purposes.
-     */
-    public String toString ()
-    {
-        final StringBuffer s = new StringBuffer ();
-        debugDump (s);
-        
-        return s.toString ();
-    }
-    
-    /**
-     * Returns the number of key-value mappings in this map.
-     */
-    public int size ()
-    {
-        return m_size;
-    }
-
-    public boolean contains (final Object key)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (key != null, "null input: key");
-        
-        // index into the corresponding hash bucket:
-        final Entry [] buckets = m_buckets;
-        final int keyHash = key.hashCode ();
-        final int bucketIndex = (keyHash & 0x7FFFFFFF) % buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if ((keyHash == entry.m_key.hashCode ()) || entry.m_key.equals (key))
-                return true;
-        }
-        
-        return false;
-    }
-    
-    /**
-     * Returns the value that is mapped to a given 'key'. Returns
-     * false if this key has never been mapped.
-     *
-     * @param key mapping key [may not be null]
-     * @param out holder for the found value [must be at least of size 1]
-     *
-     * @return 'true' if this key was mapped to an existing value
-     */
-    public boolean get (final Object key, final int [] out)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (key != null, "null input: key");
-        
-        // index into the corresponding hash bucket:
-        final Entry [] buckets = m_buckets;
-        final int keyHash = key.hashCode ();
-        final int bucketIndex = (keyHash & 0x7FFFFFFF) % buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if ((keyHash == entry.m_key.hashCode ()) || entry.m_key.equals (key))
-            {
-                out [0] = entry.m_value;
-                return true;
-            }
-        }
-        
-        return false;
-    }
-    
-    public Object [] keys ()
-    {
-        final Object [] result = new Object [m_size];
-        int scan = 0;
-        
-        for (int b = 0; b < m_buckets.length; ++ b)
-        {
-            for (Entry entry = m_buckets [b]; entry != null; entry = entry.m_next)
-            {
-                result [scan ++] = entry.m_key;
-            }
-        }
-        
-        return result;
-    }
-    
-    /**
-     * Updates the table to map 'key' to 'value'. Any existing mapping is overwritten.
-     *
-     * @param key mapping key [may not be null]
-     * @param value mapping value.
-     */
-    public void put (final Object key, final int value)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (key != null, "null input: key");
-        
-        Entry currentKeyEntry = null;
-        
-        // detect if 'key' is already in the table [in which case, set 'currentKeyEntry' to point to its entry]:
-        
-        // index into the corresponding hash bucket:
-        final int keyHash = key.hashCode ();
-        int bucketIndex = (keyHash & 0x7FFFFFFF) % m_buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        Entry [] buckets = m_buckets;
-        for (Entry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            if ((keyHash == entry.m_key.hashCode ()) || entry.m_key.equals (key))
-            {
-                currentKeyEntry = entry;
-                break;
-            }
-        }
-        
-        if (currentKeyEntry != null)
-        {
-            // replace the current value:
-                
-            currentKeyEntry.m_value = value;
-        }
-        else
-        {
-            // add a new entry:
-            
-            if (m_size >= m_sizeThreshold) rehash ();
-            
-            buckets = m_buckets;
-            bucketIndex = (keyHash & 0x7FFFFFFF) % buckets.length;
-            final Entry bucketListHead = buckets [bucketIndex];
-            final Entry newEntry = new Entry (key, value, bucketListHead);
-            buckets [bucketIndex] = newEntry;
-            
-            ++ m_size;
-        }
-    }
-    
-    /**
-     * Updates the table to map 'key' to 'value'. Any existing mapping is overwritten.
-     *
-     * @param key mapping key [may not be null]
-     */
-    public void remove (final Object key)
-    {
-        if ($assert.ENABLED) $assert.ASSERT (key != null, "null input: key");
-        
-        // index into the corresponding hash bucket:
-        final int keyHash = key.hashCode ();
-        final int bucketIndex = (keyHash  & 0x7FFFFFFF) % m_buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        Entry [] buckets = m_buckets;
-        for (Entry entry = buckets [bucketIndex], prev = entry; entry != null; )
-        {
-            final Entry next = entry.m_next;
-            
-            if ((keyHash == entry.m_key.hashCode ()) || entry.m_key.equals (key))
-            {
-                if (prev == entry)
-                    buckets [bucketIndex] = next;
-                else
-                    prev.m_next = next;
-                
-                -- m_size;     
-                break;
-            }
-            
-            prev = entry;
-            entry = next;
-        }
-    }
-
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    void debugDump (final StringBuffer out)
-    {
-        if (out != null)
-        {
-            out.append (super.toString ()); out.append (EOL);
-            out.append ("size = " + m_size + ", bucket table size = " + m_buckets.length + ", load factor = " + m_loadFactor + EOL);
-            out.append ("size threshold = " + m_sizeThreshold + EOL);
-        }
-    }
-
-    // private: ...............................................................
-
-    
-    /**
-     * The structure used for chaining colliding keys.
-     */
-    private static final class Entry
-    {
-        Entry (final Object key, final int value, final Entry next)
-        {
-            m_key = key; 
-            m_value = value;
-            m_next = next;
-        }
-        
-        Object m_key;     // reference to the value [never null]
-        int m_value;
-        
-        Entry m_next; // singly-linked list link
-        
-    } // end of nested class
-    
-
-    /**
-     * Re-hashes the table into a new array of buckets.
-     */
-    private void rehash ()
-    {
-        // TODO: it is possible to run this method twice, first time using the 2*k+1 prime sequencer for newBucketCount
-        // and then with that value reduced to actually shrink capacity. As it is right now, the bucket table can
-        // only grow in size
-        
-        final Entry [] buckets = m_buckets;
-        
-        final int newBucketCount = (m_buckets.length << 1) + 1;
-        final Entry [] newBuckets = new Entry [newBucketCount];
-
-        // rehash all entry chains in every bucket:
-        for (int b = 0; b < buckets.length; ++ b)
-        {
-            for (Entry entry = buckets [b]; entry != null; )
-            {
-                final Entry next = entry.m_next; // remember next pointer because we are going to reuse this entry
-                final int entryKeyHash = entry.m_key.hashCode () & 0x7FFFFFFF;
-            
-                // index into the corresponding new hash bucket:
-                final int newBucketIndex = entryKeyHash % newBucketCount;
-                
-                final Entry bucketListHead = newBuckets [newBucketIndex];
-                entry.m_next = bucketListHead;
-                newBuckets [newBucketIndex] = entry;                                
-                
-                entry = next;
-            }
-        }
-        
-
-        m_sizeThreshold = (int) (newBucketCount * m_loadFactor);
-        m_buckets = newBuckets;
-    }
-    
-    
-    private final float m_loadFactor; // determines the setting of m_sizeThreshold
-    
-    private Entry [] m_buckets; // table of buckets
-    private int m_size; // number of keys in the table, not cleared as of last check
-    private int m_sizeThreshold; // size threshold for rehashing
-        
-    private static final String EOL = System.getProperty ("line.separator", "\n");
-    
-} // end of class
-// ----------------------------------------------------------------------------
-
diff --git a/core/java12/com/vladium/util/Property.java b/core/java12/com/vladium/util/Property.java
deleted file mode 100644
index 814971b..0000000
--- a/core/java12/com/vladium/util/Property.java
+++ /dev/null
@@ -1,557 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Property.java,v 1.1.1.1.2.4 2004/07/16 23:32:04 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.BufferedInputStream;
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.util.Enumeration;
-import java.util.Hashtable;
-import java.util.Iterator;
-import java.util.Map;
-import java.util.Properties;
-
-/*
- * NOTE: to avoid certain build problems, this class should use only
- * core Java APIs and not any app infrastructure.
- */
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class Property
-{
-    // public: ................................................................
-
-
-    public static boolean toBoolean (final String value)
-    {
-        if (value == null)
-            return false;
-        else
-            return value.startsWith ("t") || value.startsWith ("y");
-    }
-
-    
-    /**
-     * NOTE: this does not guarantee that the result will be mutatable
-     * independently from 'overrides' or 'base', so this method
-     * should be used for read-only property only
-     * 
-     * @param overrides [null is equivalent to empty]
-     * @param base [null is equivalent to empty]
-     * 
-     * @return [never null, could be empty]
-     */
-    public static Properties combine (final Properties overrides, final Properties base)
-    {
-        // note: no defensive copies here
-         
-        if (base == null)
-        {
-            if (overrides == null)
-                return new XProperties ();
-            else
-                return overrides;
-        }
-        
-        // [assertion: base != null]
-        
-        if (overrides == null) return base;
-        
-        // [assertion: both 'overrides' and 'base' are not null]
-        
-        final Properties result = new XProperties (base);
-        
-        // note: must use propertyNames() because that is the only method that recurses
-        // into possible bases inside 'overrides'
-        
-        for (Enumeration overrideNames = overrides.propertyNames (); overrideNames.hasMoreElements (); )
-        {
-            final String n = (String) overrideNames.nextElement ();
-            final String v = overrides.getProperty (n);
-            
-            result.setProperty (n, v);
-        }
-        
-        return result;
-    }
-    
-    /**
-     * Creates a set of properties for an application with a given namespace.
-     * This method is not property aliasing-aware.
-     * 
-     * @param namespace application namespace [may not be null]
-     * @param loader classloader to use for any classloader resource lookups
-     * [null is equivalent to the applicaton classloader]
-     * @return application properties [never null, a new instance is created
-     * on each invocation]
-     */
-    public static Properties getAppProperties (final String namespace, final ClassLoader loader)
-    {
-        if (namespace == null)
-            throw new IllegalArgumentException ("null properties: appNameLC");
-        
-        final Properties appDefaults = Property.getProperties (namespace + "_default.properties", loader);
-        final Properties systemFileOverrides;
-        {
-            final String fileName = Property.getSystemProperty (namespace + ".properties");
-            final File file = fileName != null
-                ? new File (fileName)
-                : null;
-
-            systemFileOverrides = Property.getLazyPropertiesFromFile (file);
-        }
-        final Properties systemOverrides = Property.getSystemProperties (namespace);
-        final Properties resOverrides = Property.getProperties (namespace + ".properties", loader);
-        
-        return combine (resOverrides,
-               combine (systemOverrides,
-               combine (systemFileOverrides,
-                        appDefaults)));
-    }
-    
-    public static Properties getSystemProperties (final String systemPrefix)
-    {
-        // note: this method is not synchronized on purpose
-        
-        Properties result = s_systemProperties;
-        if (result == null)
-        {
-            result = new SystemPropertyLookup (systemPrefix);
-            
-            s_systemProperties = result;
-            return result;
-        }
-        
-        return result;
-    }
-    
-    public static Properties getSystemPropertyRedirects (final Map systemRedirects)
-    {
-        // note: this method is not synchronized on purpose
-        
-        Properties result = s_systemRedirects;
-        if (result == null)
-        {
-            result = new SystemRedirectsLookup (systemRedirects);
-            
-            s_systemRedirects = result;
-            return result;
-        }
-        
-        return result;
-    }
-
-
-    public static String getSystemFingerprint ()
-    {
-        // [not synchronized intentionally]
-        
-        if (s_systemFingerprint != null)
-            return s_systemFingerprint;
-        else
-        {
-            final StringBuffer s = new StringBuffer ();
-            final char delimiter = ':';
-            
-            s.append (getSystemProperty ("java.vm.name", ""));
-            s.append (delimiter);
-            s.append (getSystemProperty ("java.vm.version", ""));
-            s.append (delimiter);
-            s.append (getSystemProperty ("java.vm.vendor", ""));
-            s.append (delimiter);
-            s.append (getSystemProperty ("os.name", ""));
-            s.append (delimiter);
-            s.append (getSystemProperty ("os.version", ""));
-            s.append (delimiter);
-            s.append (getSystemProperty ("os.arch", ""));
-            
-            s_systemFingerprint = s.toString ();
-            return s_systemFingerprint;
-        }
-    }    
-    
-    public static String getSystemProperty (final String key)
-    {
-        try
-        {
-            return System.getProperty (key);
-        }
-        catch (SecurityException se)
-        {
-            return null;
-        }
-    }
-    
-    public static String getSystemProperty (final String key, final String def)
-    {
-        try
-        {
-            return System.getProperty (key, def);
-        }
-        catch (SecurityException se)
-        {
-            return def;
-        }
-    }
-    
-    /**
-     * does not throw
-     * 
-     * @param name
-     * @return
-     */
-    public static Properties getProperties (final String name)
-    {
-        Properties result = null;
-        
-        InputStream in = null;
-        try
-        {
-            in = ResourceLoader.getResourceAsStream (name);
-            if (in != null)
-            {
-                result = new XProperties ();
-                result.load (in);
-            }
-        }
-        catch (Throwable t)
-        {
-            result = null;
-        }
-        finally
-        {
-            if (in != null) try { in.close (); } catch (Throwable ignore) {}
-            in = null;
-        }
-        
-        return result;
-    }
-    
-    /**
-     * does not throw
-     * 
-     * @param name
-     * @param loader
-     * @return
-     */
-    public static Properties getProperties (final String name, final ClassLoader loader)
-    {
-        Properties result = null;
-        
-        InputStream in = null;
-        try
-        {
-            in = ResourceLoader.getResourceAsStream (name, loader);
-            if (in != null)
-            {
-                result = new XProperties ();
-                result.load (in);
-            }
-        }
-        catch (Throwable t)
-        {
-            result = null;
-        }
-        finally
-        {
-            if (in != null) try { in.close (); } catch (Throwable ignore) {}
-            in = null;
-        }
-        
-        return result;
-    }
-
-    /**
-     * Loads 'file' as a .properties file.
-     * 
-     * @param file [may not be null]
-     * @return read properties [never null]
-     * @throws IOException on any file I/O errors
-     */
-    public static Properties getPropertiesFromFile (final File file)
-        throws IOException
-    {
-        if (file == null)
-            throw new IllegalArgumentException ("null input: file");
-        
-        Properties result = null;
-        
-        InputStream in = null;
-        try
-        {
-            in = new BufferedInputStream (new FileInputStream (file), 8 * 1024);
-
-            result = new XProperties ();
-            result.load (in);
-        }
-        finally
-        {
-            if (in != null) try { in.close (); } catch (Throwable ignore) {}
-            in = null;
-        }
-        
-        return result;
-    }    
-
-    /**
-     * Returns a lazy property implementation that will read 'load' as a .properties
-     * file on first use. If there are any file I/O errors when reading the file,
-     * they will be thrown as runtime exceptions (also on first use).
-     * 
-     * @param file [can be null, which results in an empty property set returned]
-     * @return [never null]
-     */
-    public static Properties getLazyPropertiesFromFile (final File file)
-    {
-        return new FilePropertyLookup (file);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final class FilePropertyLookup extends XProperties
-    {
-        // note: due to incredibly stupid coding in java.util.Properties
-        // (getProperty() uses a non-virtual call to get(), while propertyNames()
-        // uses a virtual call to the same instead of delegating to getProperty())
-        // I must override both methods below
-        
-        public String getProperty (final String key)
-        {
-            faultContents ();
-            
-            return m_contents.getProperty (key);
-        }
-            
-        public Object get (final Object key)
-        {
-            faultContents ();
-            
-            return m_contents.get (key);
-        }
-        
-        /*
-         * Overrides Properties.keys () [this is used for debug logging only]
-         */
-        public Enumeration keys ()
-        {
-            faultContents ();
-            
-            return m_contents.keys ();
-        }
-
-
-        /**
-         * Creates a lazy property lookup based on 'src' contents.
-         * 
-         * @param src [null will result in empty property set created]
-         */
-        FilePropertyLookup (final File src)
-        {
-            m_src = src;
-        }
-        
-        /*
-         * @throws RuntimeException on file I/O failures. 
-         */
-        private synchronized void faultContents ()
-        {
-            Properties contents = m_contents;
-            if ((contents == null) && (m_src != null))
-            {
-                try
-                {
-                    contents = getPropertiesFromFile (m_src);
-                }
-                catch (RuntimeException re)
-                {
-                    throw re; // re-throw;
-                }
-                catch (Exception e)
-                {
-                    throw new RuntimeException ("exception while processing properties file [" + m_src.getAbsolutePath () + "]: " + e);
-                }
-            }
-            
-            if (contents == null)
-            {
-                contents = new XProperties (); // non-null marker
-            }
-            
-            m_contents = contents;
-        }
-        
-
-        private final File m_src; // can be null
-        private Properties m_contents; // non-null after faultContents()
-        
-    } // end of nested class
-    
-
-    private static final class SystemPropertyLookup extends XProperties
-    {
-        // note: due to incredibly stupid coding in java.util.Properties
-        // (getProperty() uses a non-virtual call to get(), while propertyNames()
-        // uses a virtual call to the same instead of delegating to getProperty())
-        // I must override both methods below
-        
-        public String getProperty (final String key)
-        {
-            return (String) get (key);
-        }
-            
-        public Object get (final Object key)
-        {
-            if (! (key instanceof String)) return null;
-            
-            String result = (String) super.get (key);
-            if (result != null) return result;
-            
-            if (m_systemPrefix != null)
-            {
-                result = getSystemProperty (m_systemPrefix.concat ((String) key), null);
-                
-                if (result != null) return result;
-            }
-            
-            return result;
-        }
-        
-        /*
-         * Overrides Properties.keys () [this is used for debug logging only]
-         */
-        public synchronized Enumeration keys ()
-        {
-            final Hashtable _propertyNames = new Hashtable ();
-            
-            if (m_systemPrefix != null)
-            {
-                try
-                {
-                    final int systemPrefixLength = m_systemPrefix.length ();
-                    
-                    for (Enumeration e = System.getProperties ().propertyNames ();
-                         e.hasMoreElements (); )
-                    {
-                        final String n = (String) e.nextElement ();
-                        
-                        if (n.startsWith (m_systemPrefix))
-                        {
-                            final String yn = n.substring (systemPrefixLength);
-                            
-                            _propertyNames.put (yn, yn);
-                        }
-                    } 
-                }
-                catch (SecurityException ignore)
-                {
-                    ignore.printStackTrace (System.out);
-                    
-                    // continue
-                }
-            }
-            
-            return _propertyNames.keys ();
-        }
-
-                
-        SystemPropertyLookup (String systemPrefix)
-        {
-            if ((systemPrefix != null) && ! systemPrefix.endsWith ("."))
-                systemPrefix = systemPrefix.concat (".");
-                
-            m_systemPrefix = systemPrefix;
-        }
-        
-        
-        private final String m_systemPrefix; // can be null [if not null, normalized to end with "."]
-        
-    } // end of nested class
-    
-    
-    private static final class SystemRedirectsLookup extends XProperties
-    {
-        // note: due to incredibly stupid coding in java.util.Properties
-        // (getProperty() uses a non-virtual call to get(), while propertyNames()
-        // uses a virtual call to the same instead of delegating to getProperty())
-        // I must override both methods below
-        
-        public String getProperty (final String key)
-        {
-            return (String) get (key);
-        }
-            
-        public Object get (final Object key)
-        {
-            if (! (key instanceof String)) return null;
-            
-            String result = (String) super.get (key);
-            if (result != null) return result;
-            
-            if (m_systemRedirects != null)
-            {
-                final String redirect = (String) m_systemRedirects.get (key);
-                
-                if (redirect != null)
-                {
-                    result = getSystemProperty (redirect, null);
-                    if (result != null) return result;
-                }
-            }
-            
-            return result;
-        }
-        
-        /*
-         * Overrides Properties.keys () [this is used for debug logging only]
-         */
-        public synchronized Enumeration keys ()
-        {
-            final Hashtable _propertyNames = new Hashtable ();
-            
-            if (m_systemRedirects != null)
-            {
-                for (Iterator i = m_systemRedirects.keySet ().iterator ();
-                     i.hasNext (); )
-                {
-                    final Object key = i.next ();                    
-                    if (key != null) _propertyNames.put (key , key);
-                }
-            }
-            
-            return _propertyNames.keys ();
-        }
-
-                
-        SystemRedirectsLookup (final Map systemRedirects)
-        {
-            m_systemRedirects = systemRedirects; // note: no defensive copy
-        }
-        
-        
-        private final Map m_systemRedirects; // can be null
-        
-    } // end of nested class
-    
-    
-    private static String s_systemFingerprint;
-    private static Properties s_systemProperties, s_systemRedirects;
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/ResourceLoader.java b/core/java12/com/vladium/util/ResourceLoader.java
deleted file mode 100644
index 13a53c1..0000000
--- a/core/java12/com/vladium/util/ResourceLoader.java
+++ /dev/null
@@ -1,127 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ResourceLoader.java,v 1.1.1.1.2.1 2004/06/20 18:24:05 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.IOException;
-import java.io.InputStream;
-import java.net.URL;
-import java.util.Enumeration;
-
-// ----------------------------------------------------------------------------
-/**
- * A static API that can be used as a drop-in replacement for
- * java.lang.ClassLoader API (the class/resource loading part). This
- * implementation is merely a wrapper around ClassLoaderResolverget.ClassLoader()
- * method.
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class ResourceLoader
-{
-    // public: ................................................................
-    
-    /**
-     * @see java.lang.ClassLoader#loadClass(java.lang.String)
-     */
-    public static Class loadClass (final String name)
-        throws ClassNotFoundException
-    {
-        final Class caller = ClassLoaderResolver.getCallerClass (1);
-        final ClassLoader loader = ClassLoaderResolver.getClassLoader (caller);
-        
-        return Class.forName (name, false, loader);
-    }
-
-    /**
-     * @see java.lang.ClassLoader#getResource(java.lang.String)
-     */    
-    public static URL getResource (final String name)
-    {
-        final Class caller = ClassLoaderResolver.getCallerClass (1);
-        final ClassLoader loader = ClassLoaderResolver.getClassLoader (caller);
-        
-        if (loader != null)
-            return loader.getResource (name);
-        else
-            return ClassLoader.getSystemResource (name);
-    }
-
-    /**
-     * @see java.lang.ClassLoader#getResourceAsStream(java.lang.String)
-     */        
-    public static InputStream getResourceAsStream (final String name)
-    {
-        final Class caller = ClassLoaderResolver.getCallerClass (1);
-        final ClassLoader loader = ClassLoaderResolver.getClassLoader (caller);
-        
-        if (loader != null)
-            return loader.getResourceAsStream (name);
-        else
-            return ClassLoader.getSystemResourceAsStream (name);
-    }
-
-    /**
-     * @see java.lang.ClassLoader#getResources(java.lang.String)
-     */            
-    public static Enumeration getResources (final String name)
-        throws IOException
-    {
-        final Class caller = ClassLoaderResolver.getCallerClass (1);
-        final ClassLoader loader = ClassLoaderResolver.getClassLoader (caller);
-        
-        if (loader != null)
-            return loader.getResources (name);
-        else
-            return ClassLoader.getSystemResources (name);
-    }
-    
-    
-    public static Class loadClass (final String name, final ClassLoader loader)
-        throws ClassNotFoundException
-    {
-        return Class.forName (name, false, loader != null ? loader : ClassLoader.getSystemClassLoader ());
-    }
-
-    public static URL getResource (final String name, final ClassLoader loader)
-    {
-        if (loader != null)
-            return loader.getResource (name);
-        else
-            return ClassLoader.getSystemResource (name);
-    }
-
-    public static InputStream getResourceAsStream (final String name, final ClassLoader loader)
-    {
-        if (loader != null)
-            return loader.getResourceAsStream (name);
-        else
-            return ClassLoader.getSystemResourceAsStream (name);
-    }
-
-    public static Enumeration getResources (final String name, final ClassLoader loader)
-        throws IOException
-    {
-        if (loader != null)
-            return loader.getResources (name);
-        else
-            return ClassLoader.getSystemResources (name);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private ResourceLoader () {} // prevent subclassing
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/SoftValueMap.java b/core/java12/com/vladium/util/SoftValueMap.java
deleted file mode 100644
index 3eefaaa..0000000
--- a/core/java12/com/vladium/util/SoftValueMap.java
+++ /dev/null
@@ -1,619 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: SoftValueMap.java,v 1.1.1.1 2004/05/09 16:57:55 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.lang.ref.Reference;
-import java.lang.ref.ReferenceQueue;
-import java.lang.ref.SoftReference;
-import java.util.Collection;
-import java.util.Map;
-import java.util.Set;
-
-// ----------------------------------------------------------------------------
-/**
- * MT-safety: an instance of this class is <I>not</I> safe for access from
- * multiple concurrent threads [even if access is done by a single thread at a
- * time]. The caller is expected to synchronize externally on an instance [the
- * implementation does not do internal synchronization for the sake of efficiency].
- * java.util.ConcurrentModificationException is not supported either.
- *
- * @author (C) 2002, Vlad Roubtsov
- */
-public
-final class SoftValueMap implements Map
-{
-    // public: ................................................................
-
-    // TODO: for caching, does clearing of entries make sense? only to save
-    // entry memory -- which does not make sense if the set of key values is not
-    // growing over time... on the other hand, if the key set is unbounded,
-    // entry clearing is needed so that the hash table does not get polluted with
-    // empty-valued entries 
-    // TODO: provide mode that disables entry clearing 
-    // TODO: add shrinking rehashes (is it worth it?)
-
-    /**
-     * Equivalent to <CODE>SoftValueMap(1, 1)</CODE>.
-     */
-    public SoftValueMap ()
-    {
-        this (1, 1);
-    }
-    
-    /**
-     * Equivalent to <CODE>SoftValueMap(11, 0.75F, getClearCheckFrequency, putClearCheckFrequency)</CODE>.
-     */
-    public SoftValueMap (final int readClearCheckFrequency, final int writeClearCheckFrequency)
-    {
-        this (11, 0.75F, readClearCheckFrequency, writeClearCheckFrequency);
-    }
-    
-    /**
-     * Constructs a SoftValueMap with specified initial capacity, load factor,
-     * and cleared value removal frequencies.
-     *
-     * @param initialCapacity initial number of hash buckets in the table
-     * [may not be negative, 0 is equivalent to 1].
-     * @param loadFactor the load factor to use to determine rehashing points
-     * [must be in (0.0, 1.0] range].
-     * @param readClearCheckFrequency specifies that every readClearCheckFrequency
-     * {@link #get} should check for and remove all mappings whose soft values
-     * have been cleared by the garbage collector [may not be less than 1].
-     * @param writeClearCheckFrequency specifies that every writeClearCheckFrequency
-     * {@link #put} should check for and remove all mappings whose soft values
-     * have been cleared by the garbage collector [may not be less than 1].
-     */
-    public SoftValueMap (int initialCapacity, final float loadFactor, final int readClearCheckFrequency, final int writeClearCheckFrequency)
-    {
-        if (initialCapacity < 0)
-            throw new IllegalArgumentException ("negative input: initialCapacity [" + initialCapacity + "]");
-        if ((loadFactor <= 0.0) || (loadFactor >= 1.0 + 1.0E-6))
-            throw new IllegalArgumentException ("loadFactor not in (0.0, 1.0] range: " + loadFactor);
-        if (readClearCheckFrequency < 1)
-            throw new IllegalArgumentException ("readClearCheckFrequency not in [1, +inf) range: " + readClearCheckFrequency);
-        if (writeClearCheckFrequency < 1)
-            throw new IllegalArgumentException ("writeClearCheckFrequency not in [1, +inf) range: " + writeClearCheckFrequency);
-        
-        if (initialCapacity == 0) initialCapacity = 1;
-        
-        m_valueReferenceQueue = new ReferenceQueue ();
-        
-        m_loadFactor = loadFactor;
-        m_sizeThreshold = (int) (initialCapacity * loadFactor);
-        
-        m_readClearCheckFrequency = readClearCheckFrequency;
-        m_writeClearCheckFrequency = writeClearCheckFrequency;
-        
-        m_buckets = new SoftEntry [initialCapacity];
-    }
-    
-    
-    // unsupported operations:
-        
-    public boolean equals (final Object rhs)
-    {
-        throw new UnsupportedOperationException ("not implemented: equals");
-    }
-    
-    public int hashCode ()
-    {
-        throw new UnsupportedOperationException ("not implemented: hashCode");
-    }
-    
-    
-    /**
-     * Overrides Object.toString() for debug purposes.
-     */
-    public String toString ()
-    {
-        final StringBuffer s = new StringBuffer ();
-        debugDump (s);
-        
-        return s.toString ();
-    }
-    
-    
-    /**
-     * Returns the number of key-value mappings in this map. Some of the values
-     * may have been cleared already but not removed from the table.<P>
-     *
-     * <B>NOTE:</B> in contrast with the java.util.WeakHashMap implementation,
-     * this is a constant time operation.
-     */
-    public int size ()
-    {
-        return m_size;
-    }
-    
-    /**
-     * Returns 'false' is this map contains key-value mappings (even if some of
-     * the values may have been cleared already but not removed from the table).<P>
-     *
-     * <B>NOTE:</B> in contrast with the java.util.WeakHashMap implementation,
-     * this is a constant time operation.
-     */
-    public boolean isEmpty ()
-    {
-        return m_size == 0;
-    }
-    
-    /**
-     * Returns the value that is mapped to a given 'key'. Returns
-     * null if (a) this key has never been mapped or (b) a previously mapped
-     * value has been cleared by the garbage collector and removed from the table.
-     *
-     * @param key mapping key [may not be null].
-     *
-     * @return Object value mapping for 'key' [can be null].
-     */
-    public Object get (final Object key)
-    {
-        if (key == null) throw new IllegalArgumentException ("null input: key");
-        
-        if ((++ m_readAccessCount % m_readClearCheckFrequency) == 0) removeClearedValues ();
-        
-        // index into the corresponding hash bucket:
-        final int keyHashCode = key.hashCode ();
-        final SoftEntry [] buckets = m_buckets;
-        final int bucketIndex = (keyHashCode & 0x7FFFFFFF) % buckets.length;
-        
-        Object result = null; 
-        
-        // traverse the singly-linked list of entries in the bucket:
-        for (SoftEntry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            final Object entryKey = entry.m_key;
-
-            if (IDENTITY_OPTIMIZATION)
-            {
-                // note: this uses an early identity comparison opimization, making this a bit
-                // faster for table keys that do not override equals() [Thread, etc]
-                if ((key == entryKey) || ((keyHashCode == entryKey.hashCode ()) && key.equals (entryKey)))
-                {
-                    final Reference ref = entry.m_softValue;
-                    result = ref.get (); // may return null to the caller
-                    
-                    // [see comment for ENQUEUE_FOUND_CLEARED_ENTRIES]
-                    if (ENQUEUE_FOUND_CLEARED_ENTRIES && (result == null))
-                    {
-                        ref.enqueue ();
-                    }
-                    
-                    return result;
-                }
-            }
-            else
-            {
-                if ((keyHashCode == entryKey.hashCode ()) && key.equals (entryKey))
-                {
-                    final Reference ref = entry.m_softValue;
-                    result = ref.get (); // may return null to the caller
-                    
-                    // [see comment for ENQUEUE_FOUND_CLEARED_ENTRIES]
-                    if (ENQUEUE_FOUND_CLEARED_ENTRIES && (result == null))
-                    {
-                        ref.enqueue ();
-                    }
-                    
-                    return result;
-                }
-            }
-        }
-        
-        return null;
-    }
-    
-    /**
-     * Updates the table to map 'key' to 'value'. Any existing mapping is overwritten.
-     *
-     * @param key mapping key [may not be null].
-     * @param value mapping value [may not be null].
-     *
-     * @return Object previous value mapping for 'key' [null if no previous mapping
-     * existed or its value has been cleared by the garbage collector and removed from the table].
-     */
-    public Object put (final Object key, final Object value)
-    {
-        if (key == null) throw new IllegalArgumentException ("null input: key");
-        if (value == null) throw new IllegalArgumentException ("null input: value");
-        
-        if ((++ m_writeAccessCount % m_writeClearCheckFrequency) == 0) removeClearedValues ();
-            
-        SoftEntry currentKeyEntry = null;
-        
-        // detect if 'key' is already in the table [in which case, set 'currentKeyEntry' to point to its entry]:
-        
-        // index into the corresponding hash bucket:
-        final int keyHashCode = key.hashCode ();
-        SoftEntry [] buckets = m_buckets;
-        int bucketIndex = (keyHashCode & 0x7FFFFFFF) % buckets.length;
-        
-        // traverse the singly-linked list of entries in the bucket:
-        for (SoftEntry entry = buckets [bucketIndex]; entry != null; entry = entry.m_next)
-        {
-            final Object entryKey = entry.m_key;
-            
-            if (IDENTITY_OPTIMIZATION)
-            {
-                // note: this uses an early identity comparison opimization, making this a bit
-                // faster for table keys that do not override equals() [Thread, etc]
-                if ((key == entryKey) || ((keyHashCode == entryKey.hashCode ()) && key.equals (entryKey)))
-                {
-                    currentKeyEntry = entry;
-                    break;
-                }
-            }
-            else
-            {
-                if ((keyHashCode == entryKey.hashCode ()) && key.equals (entryKey))
-                {
-                    currentKeyEntry = entry;
-                    break;
-                }
-            }
-        }
-        
-        if (currentKeyEntry != null)
-        {
-            // replace the current value:
-            
-            final IndexedSoftReference ref = currentKeyEntry.m_softValue;
-            final Object currentKeyValue = ref.get (); // can be null already [no need to work around the get() bug, though]
-            
-            if (currentKeyValue == null) ref.m_bucketIndex = -1; // disable removal by removeClearedValues() [need to do this because of the identity comparison there]
-            currentKeyEntry.m_softValue = new IndexedSoftReference (value, m_valueReferenceQueue, bucketIndex);
-            
-            return currentKeyValue; // may return null to the caller
-        }
-        else
-        {
-            // add a new entry:
-            
-            if (m_size >= m_sizeThreshold) rehash ();
-            
-            // recompute the hash bucket index:
-            buckets = m_buckets;
-            bucketIndex = (keyHashCode & 0x7FFFFFFF) % buckets.length;
-            final SoftEntry bucketListHead = buckets [bucketIndex];
-            final SoftEntry newEntry = new SoftEntry (m_valueReferenceQueue, key, value, bucketListHead, bucketIndex);
-            buckets [bucketIndex] = newEntry;
-            
-            ++ m_size;
-            
-            return null;
-        }
-    }
-    
-    public Object remove (final Object key)
-    {
-        if (key == null) throw new IllegalArgumentException ("null input: key");
-        
-        if ((++ m_writeAccessCount % m_writeClearCheckFrequency) == 0) removeClearedValues ();
-
-        // index into the corresponding hash bucket:
-        final int keyHashCode = key.hashCode ();
-        final SoftEntry [] buckets = m_buckets;
-        final int bucketIndex = (keyHashCode & 0x7FFFFFFF) % buckets.length;
-        
-        Object result = null;
-
-        // traverse the singly-linked list of entries in the bucket:
-        for (SoftEntry entry = buckets [bucketIndex], prev = null; entry != null; prev = entry, entry = entry.m_next)
-        {
-            final Object entryKey = entry.m_key;
-            
-            if ((IDENTITY_OPTIMIZATION && (entryKey == key)) || ((keyHashCode == entryKey.hashCode ()) && key.equals (entryKey)))
-            {
-                if (prev == null) // head of the list
-                {
-                    buckets [bucketIndex] = entry.m_next;
-                }
-                else
-                {
-                    prev.m_next = entry.m_next;
-                }
-                
-                final IndexedSoftReference ref = entry.m_softValue; 
-                result = ref.get (); // can be null already [however, no need to work around 4485942]
-                
-                // [regardless of whether the value has been enqueued or not, disable its processing by removeClearedValues() since the entire entry is removed here]
-                ref.m_bucketIndex = -1;
-                
-                // help GC:
-                entry.m_softValue = null;
-                entry.m_key = null;
-                entry.m_next = null;
-                entry = null;
-            
-                -- m_size;
-                break;
-            }
-        }
-        
-        return result;
-    }
-
-    
-    public void clear ()
-    {
-        final SoftEntry [] buckets = m_buckets;
-        
-        for (int b = 0, bLimit = buckets.length; b < bLimit; ++ b)
-        {
-            for (SoftEntry entry = buckets [b]; entry != null; )
-            {
-                final SoftEntry next = entry.m_next; // remember next pointer because we are going to reuse this entry
-
-                // [regardless of whether the value has been enqueued or not, disable its processing by removeClearedValues()]
-                entry.m_softValue.m_bucketIndex = -1;
-                
-                // help GC:
-                entry.m_softValue = null;
-                entry.m_next = null;
-                entry.m_key = null;
-                
-                entry = next;
-            }
-            
-            buckets [b] = null;
-        }
-        
-        m_size = 0;
-        m_readAccessCount = 0;
-        m_writeAccessCount = 0;
-    }
-
-
-    // unsupported operations:
-    
-    public boolean containsKey (final Object key)
-    {
-        throw new UnsupportedOperationException ("not implemented: containsKey");
-    }
-    
-    public boolean containsValue (final Object value)
-    {
-        throw new UnsupportedOperationException ("not implemented: containsValue");
-    }
-        
-    public void putAll (final Map map)
-    {
-        throw new UnsupportedOperationException ("not implemented: putAll");
-    }
-    
-    public Set keySet ()
-    {
-        throw new UnsupportedOperationException ("not implemented: keySet");
-    }
-    
-    public Set entrySet ()
-    {
-        throw new UnsupportedOperationException ("not implemented: entrySet");
-    }
-
-    public Collection values ()
-    {
-        throw new UnsupportedOperationException ("not implemented: values");
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    
-    void debugDump (final StringBuffer out)
-    {
-        if (out != null)
-        {
-            out.append (getClass ().getName ().concat ("@").concat (Integer.toHexString (System.identityHashCode (this)))); out.append (EOL);
-            out.append ("size = " + m_size + ", bucket table size = " + m_buckets.length + ", load factor = " + m_loadFactor + EOL);
-            out.append ("size threshold = " + m_sizeThreshold + ", get clear frequency = " + m_readClearCheckFrequency + ", put clear frequency = " + m_writeClearCheckFrequency + EOL);
-            out.append ("get count: " + m_readAccessCount + ", put count: " + m_writeAccessCount + EOL);
-        }
-    }
-
-    // private: ...............................................................
-
-
-    /**
-     * An extension of WeakReference that can store an index of the bucket it
-     * is associated with.
-     */
-    static class IndexedSoftReference extends SoftReference
-    {
-        IndexedSoftReference (final Object referent, ReferenceQueue queue, final int bucketIndex)
-        {
-            super (referent, queue);
-            
-            m_bucketIndex = bucketIndex;
-        }
-        
-        int m_bucketIndex;
-        
-    } // end of nested class
-    
-    
-    /**
-     * The structure used for chaining colliding keys.
-     */
-    static class SoftEntry
-    {
-        SoftEntry (final ReferenceQueue valueReferenceQueue, final Object key, Object value, final SoftEntry next, final int bucketIndex)
-        {
-            m_key = key;
-            
-            m_softValue = new IndexedSoftReference (value, valueReferenceQueue, bucketIndex); // ... do not retain a strong reference to the value
-            value = null;
-            
-            m_next = next;
-        }
-        
-        IndexedSoftReference m_softValue; // soft reference to the value [never null]
-        Object m_key;  // strong reference to the key [never null]
-        
-        SoftEntry m_next; // singly-linked list link
-        
-    } // end of nested class
-    
-
-    /**
-     * Re-hashes the table into a new array of buckets. During the process
-     * cleared value entries are discarded, making for another efficient cleared
-     * value removal method.
-     */
-    private void rehash ()
-    {
-        // TODO: it is possible to run this method twice, first time using the 2*k+1 prime sequencer for newBucketCount
-        // and then with that value reduced to actually shrink capacity. As it is right now, the bucket table can
-        // only grow in size
-        
-        final SoftEntry [] buckets = m_buckets;
-        
-        final int newBucketCount = (m_buckets.length << 1) + 1;
-        final SoftEntry [] newBuckets = new SoftEntry [newBucketCount];
-        
-        int newSize = 0;
-        
-        // rehash all entry chains in every bucket:
-        for (int b = 0, bLimit = buckets.length; b < bLimit; ++ b)
-        {
-            for (SoftEntry entry = buckets [b]; entry != null; )
-            {
-                final SoftEntry next = entry.m_next; // remember next pointer because we are going to reuse this entry
-                
-                IndexedSoftReference ref = entry.m_softValue; // get the soft value reference
-                                
-                Object entryValue = ref.get (); // convert the soft reference to a local strong one
-            
-                // skip entries whose keys have been cleared: this also saves on future removeClearedValues() work
-                if (entryValue != null)
-                {
-                    // [assertion: 'softValue' couldn't have been enqueued already and can't be enqueued until strong reference in 'entryKey' is nulled out]
-                    
-                    // index into the corresponding new hash bucket:
-                    final int entryKeyHashCode = entry.m_key.hashCode ();
-                    final int newBucketIndex = (entryKeyHashCode & 0x7FFFFFFF) % newBucketCount;
-                    
-                    final SoftEntry bucketListHead = newBuckets [newBucketIndex];
-                    entry.m_next = bucketListHead;
-                    newBuckets [newBucketIndex] = entry;
-                    
-                    // adjust bucket index:
-                    ref.m_bucketIndex = newBucketIndex;
-            
-                    ++ newSize;
-                    
-                    entryValue = null;
-                }
-                else
-                {
-                    // ['softValue' may or may not have been enqueued already]
-                    
-                    // adjust bucket index:
-                    // [regardless of whether 'softValue' has been enqueued or not, disable its removal by removeClearedValues() since the buckets get restructured]
-                    ref.m_bucketIndex = -1;
-                }
-                
-                entry = next;
-            }
-        }
-        
-        if (DEBUG)
-        {
-            if (m_size > newSize) System.out.println ("DEBUG: rehash() cleared " + (m_size - newSize) + " values, new size = " + newSize);
-        }
-        
-        m_size = newSize;
-        m_sizeThreshold = (int) (newBucketCount * m_loadFactor);
-        m_buckets = newBuckets;
-    }
-    
-
-    /**
-     * Removes all entries whose soft values have been cleared _and_ enqueued.
-     * See comments below for why this is safe wrt to rehash().
-     */
-    private void removeClearedValues ()
-    {
-        int count = 0;
-        
-next:   for (Reference _ref; (_ref = m_valueReferenceQueue.poll ()) != null; )
-        {
-            // remove entry containing '_ref' using its bucket index and identity comparison:
-            
-            // index into the corresponding hash bucket:
-            final int bucketIndex = ((IndexedSoftReference) _ref).m_bucketIndex;
-            
-            if (bucketIndex >= 0) // skip keys that were already removed by rehash()
-            {
-                // [assertion: this reference was not cleared when the last rehash() ran and so its m_bucketIndex is correct]
-                
-                // traverse the singly-linked list of entries in the bucket:
-                for (SoftEntry entry = m_buckets [bucketIndex], prev = null; entry != null; prev = entry, entry = entry.m_next)
-                {
-                    if (entry.m_softValue == _ref)
-                    {
-                        if (prev == null) // head of the list
-                        {
-                            m_buckets [bucketIndex] = entry.m_next;
-                        }
-                        else
-                        {
-                            prev.m_next = entry.m_next;
-                        }
-                    
-                        entry.m_softValue = null;
-                        entry.m_key = null;
-                        entry.m_next = null;
-                        entry = null;
-                    
-                        -- m_size;
-                        
-                        if (DEBUG) ++ count;
-                        continue next;
-                    }
-                }
-                
-                // no match found this can happen if a soft value got replaced by a put
-                
-                final StringBuffer msg = new StringBuffer ("removeClearedValues(): soft reference [" + _ref + "] did not match within bucket #" + bucketIndex + EOL);
-                debugDump (msg);
-            
-                throw new Error (msg.toString ());
-            }
-            // else: it has already been removed by rehash() or other methods
-        }
-        
-        if (DEBUG)
-        {
-            if (count > 0) System.out.println ("DEBUG: removeClearedValues() cleared " + count + " keys, new size = " + m_size);
-        }
-    }
-    
-    
-    private final ReferenceQueue m_valueReferenceQueue; // reference queue for all references used by SoftEntry objects used by this table
-    private final float m_loadFactor; // determines the setting of m_sizeThreshold
-    private final int m_readClearCheckFrequency, m_writeClearCheckFrequency; // parameters determining frequency of running removeClearedKeys() by get() and put()/remove(), respectively
-    
-    private SoftEntry [] m_buckets; // table of buckets
-    private int m_size; // number of values in the table, not cleared as of last check
-    private int m_sizeThreshold; // size threshold for rehashing
-    private int m_readAccessCount, m_writeAccessCount;
-    
-    private static final String EOL = System.getProperty ("line.separator", "\n");
-    
-    private static final boolean IDENTITY_OPTIMIZATION          = true;
-    
-    // setting this to 'true' is an optimization and a workaround for bug 4485942:
-    private static final boolean ENQUEUE_FOUND_CLEARED_ENTRIES  = true; 
-    
-    private static final boolean DEBUG = false;
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/util/Strings.java b/core/java12/com/vladium/util/Strings.java
deleted file mode 100644
index 446812e..0000000
--- a/core/java12/com/vladium/util/Strings.java
+++ /dev/null
@@ -1,299 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Strings.java,v 1.1.1.1 2004/05/09 16:57:55 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.File;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
-import java.util.StringTokenizer;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class Strings
-{
-    // public: ................................................................
-    
-    
-    public static final String WHITE_SPACE = " \t\r\n";
-    
-    
-    //TODO: add duplicate removal
-    public static String toListForm (final String [] strings, final char delimiter)
-    {
-        if (strings == null) return null;
-        if (strings.length == 0) return "";
-        
-        final StringBuffer s = new StringBuffer ();
-        for (int i = 0, iLimit = strings.length; i < iLimit; ++ i)
-        {
-            if (i != 0) s.append (delimiter);
-            s.append (strings [i]);
-        }
-        
-        return s.toString ();
-    }
-    
-    public static String [] removeDuplicates (final String [] strings, final boolean removeNull)
-    {
-        if (strings == null) return strings;
-        
-        final int length = strings.length;
-        if (length == 0) return strings;
-        
-        final Set /* String */ _strings = new HashSet (length);
-        final List /* String */ _result = new ArrayList (length);
-        
-        for (int i = 0; i < length; ++ i)
-        {
-            final String s = strings [i];
-            if (removeNull && (s == null)) continue;
-            
-            if (_strings.add (s)) _result.add (s);
-        }
-        
-        final int resultLength = _result.size (); 
-        if (resultLength == length)
-            return strings;
-        else
-        {
-            final String [] result = new String [resultLength];
-            _result.toArray (result);
-            
-            return result; 
-        }
-    }
-    
-    /**
-     * Also removes duplicates.
-     * 
-     * @param strings
-     * @param delimiters
-     * @param removeNull
-     * @return
-     */
-    public static String [] merge (final String [] strings, final String delimiters, final boolean removeNull)
-    {
-        if (strings == null) return strings;
-        
-        final int length = strings.length;
-        if (length == 0) return strings;
-        
-        if ((delimiters == null) || (delimiters.length () == 0))
-            throw new IllegalArgumentException ("null/empty input: delimiters");
-        
-        final Set /* String */ _strings = new HashSet (length);
-        final List /* String */ _result = new ArrayList (length);
-        
-        for (int i = 0; i < length; ++ i)
-        {
-            final String s = strings [i];
-            if (removeNull && (s == null)) continue;
-            
-            final StringTokenizer tokenizer = new StringTokenizer (s, delimiters);
-            while (tokenizer.hasMoreTokens ())
-            {
-                final String ss = tokenizer.nextToken ();
-                if (_strings.add (ss)) _result.add (ss);
-            }
-        }
-        
-        final String [] result = new String [_result.size ()];
-        _result.toArray (result);
-            
-        return result; 
-    }
-    
-    /**
-     * Removes duplicates.
-     * 
-     * @param delimiters
-     * @param processAtFiles
-     * @return
-     * @throws IOException
-     */
-    public static String [] mergeAT (final String [] strings, final String delimiters, final boolean processAtFiles)
-        throws IOException
-    {
-        if (! processAtFiles)
-            return merge (strings, delimiters, true);
-        else
-        {
-            if (strings == null) return strings;
-        
-            final int length = strings.length;
-            if (length == 0) return strings;
-            
-            if ((delimiters == null) || (delimiters.length () == 0))
-                throw new IllegalArgumentException ("null/empty input: delimiters");
-            
-            final Set /* String */ _strings = new HashSet (length);
-            final List /* String */ _result = new ArrayList (length);
-            
-            for (int i = 0; i < length; ++ i)
-            {
-                final String s = strings [i];
-                if (s == null) continue;
-                
-                final StringTokenizer tokenizer = new StringTokenizer (s, delimiters);
-                while (tokenizer.hasMoreTokens ())
-                {
-                    final String ss = tokenizer.nextToken ();
-                        
-                    if (ss.startsWith ("@"))
-                    {
-                        final String [] fileList = Files.readFileList (new File (ss.substring (1)));
-                        for (int j = 0; j < fileList.length; ++ j)
-                        {
-                            final String sss = fileList [j];
-                            if (_strings.add (sss)) _result.add (sss);
-                        }
-                    }
-                    else if (_strings.add (ss)) _result.add (ss);
-                }
-            }
-            
-            final String [] result = new String [_result.size ()];
-            _result.toArray (result);
-                
-            return result;
-        }
-    }
-    
-    /**
-     * HTML attribute values can be quoted using either double or single quotes.
-     * Depending on the type of quote used, the other kind can be used unescaped
-     * within the attribute value. This method assumes that only double quotes
-     * are used for delimiting, hence this is the only kind that is escaped.
-     */
-    public static void HTMLEscape (final String s, final StringBuffer append)
-    {
-        if (s == null) throw new IllegalArgumentException ("null input: s");
-        if (append == null) throw new IllegalArgumentException ("null input: append");
-        
-        final char [] chars;
-        if (USE_GET_CHARS) chars = s.toCharArray (); 
-        
-        for (int i = 0, iLimit = s.length (); i < iLimit; ++ i)
-        {
-            final char c = USE_GET_CHARS ? chars [i] : s.charAt (i);
-            
-            switch (c)
-            {
-                case '<':
-                    append.append ("&lt;");
-                    break;
-                    
-                case '>':
-                    append.append ("&gt;");
-                    break;
-
-                case '"':
-                    append.append ("&#34;");
-                    break;
-                    
-                case '&':
-                    append.append ("&amp;");
-                    break;
-                
-                default:
-                    append.append (c);    
-                
-            } // end of switch
-        }
-    }
-    
-    /**
-     * Same as {@link #HTMLEscape(String, StringBuffer)} but also replaces spaces
-     * with "&nbsp;"'s, which is handy for escaping code. 
-     */
-    public static void HTMLEscapeNB (final String s, final StringBuffer append)
-    {
-        if (s == null) throw new IllegalArgumentException ("null input: s");
-        if (append == null) throw new IllegalArgumentException ("null input: append");
-        
-        final char [] chars;
-        if (USE_GET_CHARS) chars = s.toCharArray (); 
-        
-        for (int i = 0, iLimit = s.length (); i < iLimit; ++ i)
-        {
-            final char c = USE_GET_CHARS ? chars [i] : s.charAt (i);
-            
-            switch (c)
-            {
-                case ' ':
-                    append.append ('\u00A0'); // don't use "&#160;": a waste of space
-                    break;
-                    
-                case '\t':
-                    append.append ("\u00A0\u00A0\u00A0\u00A0\u00A0\u00A0\u00A0\u00A0"); // TODO: define a prop for this
-                    break;
-                    
-//                case '-':
-//                    append.append ((char) 0x8209);
-//                    break;
-                    
-                case '<':
-                    append.append ("&lt;");
-                    break;
-                    
-                case '>':
-                    append.append ("&gt;");
-                    break;
-
-                case '"':
-                    append.append ("&#34;");
-                    break;
-                    
-                case '&':
-                    append.append ("&amp;");
-                    break;
-                
-                default:
-                    append.append (c);    
-                
-            } // end of switch
-        }
-    }
-    
-    public static String HTMLEscape (final String s)
-    {
-        final StringBuffer buf = new StringBuffer ();
-        HTMLEscape (s, buf);
-        
-        return buf.toString ();
-    }
-    
-    public static String HTMLEscapeSP (final String s)
-    {
-        final StringBuffer buf = new StringBuffer ();
-        HTMLEscapeNB (s, buf);
-        
-        return buf.toString ();
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private Strings () {} // prevent subclassing
-    
-    
-    private static final boolean USE_GET_CHARS = true;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/WCMatcher.java b/core/java12/com/vladium/util/WCMatcher.java
deleted file mode 100644
index 2c4dfe5..0000000
--- a/core/java12/com/vladium/util/WCMatcher.java
+++ /dev/null
@@ -1,368 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: WCMatcher.java,v 1.1.1.1 2004/05/09 16:57:56 vlad_r Exp $
- */
-package com.vladium.util;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2002
- */
-public
-abstract class WCMatcher
-{
-    // public: ................................................................
-    
-
-    public static WCMatcher compile (final String pattern)
-    {
-        if (pattern == null) throw new IllegalArgumentException ("null input: pattern");
-        
-        final char [] chars = pattern.toCharArray (); // is this faster than using charAt()?
-        final int charsLength = chars.length;
-        
-        if (charsLength == 0)
-            return EMPTY_MATCHER; // TODO: should be an EMPTY_MATCHER
-        else
-        {
-            int patternLength = 0, starCount = 0, questionCount = 0;
-            boolean star = false;
-            
-            for (int c = 0; c < charsLength; ++ c)
-            {
-                final char ch = chars [c];
-                if (ch == '*')
-                {
-                    if (! star)
-                    {
-                        star = true;
-                        ++ starCount; 
-                        chars [patternLength ++] = '*';
-                    }
-                }
-                else
-                {
-                    star = false;
-                    if (ch == '?') ++ questionCount;
-                    chars [patternLength ++] = ch;
-                }
-            }
-            
-            // [assertion: patternLength > 0]
-            
-            if ((starCount == 1) && (questionCount == 0))
-            {
-                if (patternLength == 1)
-                    return ALL_MATCHER;
-                else if (chars [0] == '*')
-                    return new EndsWithMatcher (chars, patternLength);
-                else if (chars [patternLength - 1] == '*')
-                    return new StartsWithMatcher (chars, patternLength);
-            }
-            
-            return new PatternMatcher (chars, patternLength);
-        }
-    }
-    
-    public abstract boolean matches (String s);
-    public abstract boolean matches (char [] chars);
-
-        
-//    private boolean matches (int pi, int si, final char [] string)
-//    {
-//        System.out.println ("pi = " + pi + ", si = " + si);
-//        
-//        if (pi == m_pattern.length)
-//            return si == string.length;
-//        else
-//        {
-//            switch (m_pattern [pi])
-//            {
-//                case '?':
-//                {
-//                    return (si < string.length) && matches (pi + 1, si + 1, string);
-//                }
-//                
-//                case '*':
-//                {
-//                    return matches (pi + 1, si, string) || ((si < string.length) && matches (pi, si + 1, string));
-//                }
-//                
-//                default:
-//                {
-//                    return (si < string.length) && (m_pattern [pi] == string [si]) && matches (pi + 1, si + 1, string);
-//                }
-//                
-//            } // end of switch
-//        }
-//    }
-    
-
-        
-    // protected: .............................................................
-    
-    // package: ...............................................................
-
-
-    WCMatcher () {}
-    
-    // private: ...............................................................
-    
-    
-    private static final class AllMatcher extends WCMatcher
-    {
-        public final boolean matches (final String s)
-        {
-            if (s == null) throw new IllegalArgumentException  ("null input: s");
-            
-            return true;
-        }
-        
-        public final boolean matches (final char [] chars)
-        {
-            if (chars == null) throw new IllegalArgumentException  ("null input: chars");
-            
-            return true;
-        }
-        
-    } // end of nested class
-    
-
-    private static final class EmptyMatcher extends WCMatcher
-    {
-        public final boolean matches (final String s)
-        {
-            if (s == null) throw new IllegalArgumentException  ("null input: s");
-            
-            return false;
-        }
-        
-        public final boolean matches (final char [] chars)
-        {
-            if (chars == null) throw new IllegalArgumentException  ("null input: chars");
-            
-            return chars.length == 0;
-        }
-        
-    } // end of nested class
-    
-    
-    private static final class StartsWithMatcher extends WCMatcher
-    {
-        public final boolean matches (final String s)
-        {
-            if (s == null) throw new IllegalArgumentException  ("null input: s");
-            
-            return s.startsWith (m_prefix);
-        }
-        
-        public final boolean matches (final char [] chars)
-        {
-            if (chars == null) throw new IllegalArgumentException  ("null input: chars");
-            
-            final char [] prefixChars = m_prefixChars;
-            final int prefixLength = prefixChars.length - 1;
-            
-            if (chars.length < prefixLength) return false;
-            
-            for (int c = 0; c < prefixLength; ++ c)
-            {
-                if (chars [c] != prefixChars [c]) return false; 
-            }
-            
-            return true;
-        }
-        
-        StartsWithMatcher (final char [] pattern, final int patternLength)
-        {
-            m_prefixChars = pattern;            
-            m_prefix = new String (pattern, 0, patternLength - 1);
-        }
-        
-        private final char [] m_prefixChars;
-        private final String m_prefix;
-        
-    } // end of nested class
-    
-    
-    private static final class EndsWithMatcher extends WCMatcher
-    {
-        public final boolean matches (final String s)
-        {
-            if (s == null) throw new IllegalArgumentException  ("null input: s");
-            
-            return s.endsWith (m_suffix);
-        }
-        
-        public final boolean matches (final char [] chars)
-        {
-            if (chars == null) throw new IllegalArgumentException  ("null input: chars");
-            
-            final char [] suffixChars = m_suffixChars;
-            final int suffixLength = suffixChars.length - 1;
-            final int charsLength = chars.length;
-            
-            if (charsLength < suffixLength) return false;
-            
-            for (int c = 0; c < suffixLength; ++ c)
-            {
-                if (chars [charsLength - 1 - c] != suffixChars [suffixLength - c]) return false; 
-            }
-            
-            return true;
-        }
-        
-        EndsWithMatcher (final char [] pattern, final int patternLength)
-        {
-            m_suffixChars = pattern;
-            m_suffix = new String (pattern, 1, patternLength - 1);
-        }
-        
-        private final char [] m_suffixChars;
-        private final String m_suffix;
-        
-    } // end of nested class
-    
-
-    private static final class PatternMatcher extends WCMatcher
-    {
-        public final boolean matches (final String s)
-        {
-            if (s == null) throw new IllegalArgumentException  ("null input: s");
-
-            final char [] string = s.toCharArray (); // implies an array copy; is this faster than using charAt()?
-            final int stringLength = string.length;
-
-            final char [] pattern = m_pattern;
-            final int patternLength = m_patternLength;
-            
-            // [assertion: patternLength > 0]
-            
-            int si = 0, pi = 0;
-            boolean star = false;
-            
-            
-      next: while (true)
-            {
-                //System.out.println ("pi = " + pi + ", si = " + si);
-                
-                int i = 0;
-                for ( ; pi + i < patternLength; ++ i)
-                {
-                    final char patternChar = pattern [pi + i];
-                     
-                    if (patternChar == '*')
-                    {
-                        si += i;
-                        pi += (i + 1);
-                        
-                        star = true;
-                        continue next;
-                    }
-                    
-                    final int si_i = si + i;
-                     
-                    if (si_i == stringLength) return false;
-                    
-                    if (patternChar != string [si_i])
-                    {
-                        if (patternChar == '?') continue;
-                        
-                        if (! star) return false;
-                        ++ si;
-                        
-                        continue next;
-                    }
-                    
-                } // end of for
-                
-                if (si + i == stringLength) return true;
-                
-                if (! star) return false;
-                ++ si;
-                
-                // [continue next;]
-            }
-        }
-        
-        
-        public final boolean matches (final char [] string)
-        {
-            if (string == null) throw new IllegalArgumentException  ("null input: string");
-
-            final int stringLength = string.length;
-
-            final char [] pattern = m_pattern;
-            final int patternLength = m_patternLength;
-            
-            // [assertion: patternLength > 0]
-            
-            int si = 0, pi = 0;
-            boolean star = false;
-            
-            
-      next: while (true)
-            {
-                //System.out.println ("pi = " + pi + ", si = " + si);
-                
-                int i = 0;
-                for ( ; pi + i < patternLength; ++ i)
-                {
-                    final char patternChar = pattern [pi + i];
-                     
-                    if (patternChar == '*')
-                    {
-                        si += i;
-                        pi += (i + 1);
-                        
-                        star = true;
-                        continue next;
-                    }
-                    
-                    final int si_i = si + i;
-                     
-                    if (si_i == stringLength) return false;
-                    
-                    if (patternChar != string [si_i])
-                    {
-                        if (patternChar == '?') continue;
-                        
-                        if (! star) return false;
-                        ++ si;
-                        
-                        continue next;
-                    }
-                    
-                } // end of for
-                
-                if (si + i == stringLength) return true;
-                
-                if (! star) return false;
-                ++ si;
-                
-                // [continue next;]
-            }
-        }
-        
-        PatternMatcher (final char [] pattern, final int patternLength)
-        {
-            m_pattern = pattern;
-            m_patternLength = patternLength;
-        }
-        
-        
-        private final char [] m_pattern;
-        private final int m_patternLength;
-        
-    } // end of nested class
-
-        
-    private static final WCMatcher ALL_MATCHER = new AllMatcher ();
-    private static final WCMatcher EMPTY_MATCHER = new EmptyMatcher ();
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/XProperties.java b/core/java12/com/vladium/util/XProperties.java
deleted file mode 100644
index a09d82d..0000000
--- a/core/java12/com/vladium/util/XProperties.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: XProperties.java,v 1.1.1.1 2004/05/09 16:57:56 vlad_r Exp $
- */
-package com.vladium.util;
-
-import java.io.PrintStream;
-import java.io.PrintWriter;
-import java.util.Enumeration;
-import java.util.Iterator;
-import java.util.Properties;
-import java.util.Set;
-import java.util.TreeSet;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-class XProperties extends Properties
-{
-    // public: ................................................................
-    
-    
-    public XProperties ()
-    {
-    }
-    
-    public XProperties (final Properties base)
-    {
-        super (base);
-    }
-    
-    public void list (final PrintStream out)
-    {
-        final Set /* String */ _propertyNames = new TreeSet ();
-        
-        // note: must use propertyNames() because that is the only method that recurses
-        for (Enumeration propertyNames = propertyNames (); propertyNames.hasMoreElements (); )
-        {
-            _propertyNames.add (propertyNames.nextElement ());
-        }
-        
-        for (Iterator i = _propertyNames.iterator (); i.hasNext (); )
-        {
-            final String n = (String) i.next ();
-            final String v = getProperty (n);
-            
-            out.println (n + ":\t[" + v + "]");
-        }
-    }
-    
-    public void list (final PrintWriter out)
-    {
-        final Set /* String */ _propertyNames = new TreeSet ();
-        
-        // note: must use propertyNames() because that is the only method that recurses
-        for (Enumeration propertyNames = propertyNames (); propertyNames.hasMoreElements (); )
-        {
-            _propertyNames.add (propertyNames.nextElement ());
-        }
-        
-        for (Iterator i = _propertyNames.iterator (); i.hasNext (); )
-        {
-            final String n = (String) i.next ();
-            final String v = getProperty (n);
-            
-            out.println (n + ":\t[" + v + "]");
-        }
-    }
-    
-    // protected: .............................................................
-    
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/args/IOptsParser.java b/core/java12/com/vladium/util/args/IOptsParser.java
deleted file mode 100644
index 38cbbea..0000000
--- a/core/java12/com/vladium/util/args/IOptsParser.java
+++ /dev/null
@@ -1,78 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IOptsParser.java,v 1.1.1.1 2004/05/09 16:57:56 vlad_r Exp $
- */
-package com.vladium.util.args;
-
-import java.io.PrintWriter;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2002
- */
-public
-interface IOptsParser
-{
-    // public: ................................................................
-
-    int SHORT_USAGE     = 1;
-    int DETAILED_USAGE  = 2;
-
-    interface IOpt
-    {
-        String getName ();
-        String getCanonicalName ();
-        
-        String getPatternPrefix ();
-        
-        int getValueCount ();
-        String getFirstValue ();
-        String [] getValues ();
-      
-    } // end of interface
-    
-    
-    interface IOpts
-    {
-        /**
-         * 0: none, 1: short, 2: detailed
-         * 
-         * @return
-         */
-        int usageRequestLevel ();
-        void error (PrintWriter out, int width);
-        
-        IOpt [] getOpts ();
-        boolean hasArg (String name);
-        
-        IOpt [] getOpts (String pattern);
-        
-        /**
-         * 
-         * @return [never null, could be empty]
-         */
-        String [] getFreeArgs ();
-        
-    } // end of interface
-    
-    void usage (PrintWriter out, int level, int width);
-    IOpts parse (String [] args);
-    
-    abstract class Factory
-    {
-        // TODO: pass short/long usage opt names in?
-        
-        public static IOptsParser create (final String metadataResourceName, final ClassLoader loader,
-                                          final String msgPrefix, final String [] usageOpts)
-        {
-            return new OptsParser (metadataResourceName, loader, msgPrefix, usageOpts);
-        }
-        
-    } // end of nested class
-    
-} // end of interface
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/args/OptsParser.java b/core/java12/com/vladium/util/args/OptsParser.java
deleted file mode 100644
index 9030d66..0000000
--- a/core/java12/com/vladium/util/args/OptsParser.java
+++ /dev/null
@@ -1,1598 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: OptsParser.java,v 1.1.1.1 2004/05/09 16:57:57 vlad_r Exp $
- */
-package com.vladium.util.args;
-
-import java.io.CharArrayWriter;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.InputStreamReader;
-import java.io.PrintWriter;
-import java.io.Reader;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
-import com.vladium.util.IConstants;
-import com.vladium.util.ResourceLoader;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2002
- */
-final class OptsParser implements IOptsParser
-{
-    // public: ................................................................
-
-    // TODO: #-comments
-    // TODO: prefixing for error messages
-    // TODO: support var subst (main class name, etc)
-    // TODO: support short/full usage
-    // TODO: support marking opts as for displayable in full usage only
-    
-    public synchronized void usage (final PrintWriter out, final int level, final int width)
-    {
-        // TODO: use width
-        // TODO: cache?
-        
-        final String prefix = OPT_PREFIXES [CANONICAL_OPT_PREFIX];
-        
-        for (Iterator i = m_metadata.getOptDefs (); i.hasNext (); )
-        {
-            final OptDef optdef = (OptDef) i.next ();
-            
-            if ((level < 2) && optdef.isDetailedOnly ()) // skip detailed usage only options 
-                continue;
-            
-            final StringBuffer line = new StringBuffer ("  ");
-            
-            final String canonicalName = optdef.getCanonicalName ();
-            final boolean isPattern = optdef.isPattern (); 
-             
-            line.append (prefix);
-            line.append (canonicalName);
-            if (isPattern) line.append ('*');
-            
-            final String [] names = optdef.getNames ();
-            for (int n = 0; n < names.length; ++ n)
-            {
-                final String name = names [n];
-                if (! name.equals (canonicalName))
-                {
-                    line.append (", ");
-                    
-                    line.append (prefix);
-                    line.append (name);
-                    if (isPattern) line.append ('*');
-                }
-            }
-
-            final String vmnemonic = optdef.getValueMnemonic ();
-            if (vmnemonic != null)
-            {
-                line.append (' ');
-                line.append (vmnemonic);
-            }
-
-            
-            int padding = 16 - line.length ();
-            if (padding < 2)
-            {
-                // end the current line
-                out.println (line);
-                
-                line.setLength (0);
-                for (int p = 0; p < 16; ++ p) line.append (' ');
-            }
-            else
-            {          
-                for (int p = 0; p < padding; ++ p) line.append (' ');
-            }
-            
-            if (optdef.isRequired ()) line.append ("{required} ");
-            line.append (optdef.getDescription ());
-            
-            out.println (line);
-        }
-        
-        if (level < DETAILED_USAGE)
-        {
-            final OptDef usageOptDef = m_metadata.getUsageOptDef ();
-            if ((usageOptDef != null) && (usageOptDef.getNames () != null) && (usageOptDef.getNames ().length > 1))
-            {
-                out.println (); 
-                out.println ("  {use '" + usageOptDef.getNames () [1] + "' option to see detailed usage help}");
-            }
-        }
-    }
-    
-    public synchronized IOpts parse (final String [] args)
-    {
-        if (args == null) throw new IllegalArgumentException ("null input: args");
-        
-        final Opts opts = new Opts ();
-        
-        {
-            final String [] nv = new String [2]; // out buffer for getOptNameAndValue()
-            final String [] pp = new String [1]; // out buffer for getOptDef()
-            
-            // running state/current vars:
-            int state = STATE_OPT;
-            OptDef optdef = null;
-            Opt opt = null;
-            String value = null;
-            int valueCount = 0;
-            
-            int a;
-      scan: for (a = 0; a < args.length; )
-            {
-                final String av = args [a];
-                if (av == null) throw new IllegalArgumentException ("null input: args[" + a + "]");
-                
-                //System.out.println ("[state: " + state + "] av = " + av);
-                
-                switch (state)
-                {
-                    case STATE_OPT:
-                    {
-                        if (isOpt (av, valueCount, optdef))
-                        {
-                            // 'av' looks like an option: get its name and see if it
-                            // is in the metadata
-                            
-                            valueCount = 0;
-                           
-                            getOptNameAndValue (av, nv); // this can leave nv[1] as null
-                           
-                            // [assertion: nv [0] != null]
-                           
-                            final String optName = nv [0]; // is not necessarily canonical
-                            optdef = m_metadata.getOptDef (optName, pp); // pp [0] is always set by this
-                           
-                            if (optdef == null)
-                            {
-                                // unknown option:
-                               
-                                // TODO: coded messages?
-                                opts.addError (formatMessage ("unknown option \'" + optName + "\'"));
-                               
-                                state = STATE_ERROR;
-                            }
-                            else
-                            {
-                                // merge if necessary:
-                                
-                                final String canonicalName = getOptCanonicalName (optName, optdef);
-                                final String patternPrefix = pp [0];
-    
-                                opt = opts.getOpt (canonicalName);
-                                
-                                if (optdef.isMergeable ())
-                                {
-                                    if (opt == null)
-                                    {
-                                        opt = new Opt (optName, canonicalName, patternPrefix);
-                                        opts.addOpt (opt, optdef, optName);
-                                    }
-                                }
-                                else
-                                {
-                                    if (opt == null)
-                                    {
-                                        opt = new Opt (optName, canonicalName, patternPrefix);
-                                        opts.addOpt (opt, optdef, optName);
-                                    }
-                                    else
-                                    {
-                                        opts.addError (formatMessage ("option \'" + optName + "\' cannot be specified more than once"));
-                               
-                                        state = STATE_ERROR;
-                                    }
-                                }
-
-                                value = nv [1];
-                                
-                                if (value == null) ++ a;
-                                state = STATE_OPT_VALUE;
-                            }
-                        }
-                        else
-                        {
-                            // not in STATE_OPT_VALUE and 'av' does not look
-                            // like an option: the rest of args are free
-                           
-                            state = STATE_FREE_ARGS;
-                        }
-                    }
-                    break;
-                    
-                    
-                    case STATE_OPT_VALUE:
-                    {
-                        // [assertion: opt != null and optdef != null]
-                        
-                        if (value != null)
-                        {
-                            // value specified explicitly using the <name>separator<value> syntax:
-                            // [don't shift a]
-                            
-                            valueCount = 1;
-                             
-                            final int [] cardinality = optdef.getValueCardinality ();
-                            
-                            if (cardinality [1] < 1)
-                            {
-                                opts.addError (formatMessage ("option \'" + opt.getName () + "\' does not accept values: \'" + value + "\'"));
-                               
-                                state = STATE_ERROR;
-                            }
-                            else
-                            {
-                                ++ a;
-                                opt.addValue (value);
-                            }
-                        }
-                        else
-                        {
-                            value = args [a];
-                            
-                            final int [] cardinality = optdef.getValueCardinality ();
-                        
-                            if (isOpt (value, valueCount, optdef))
-                            {
-                                if (valueCount < cardinality [0])
-                                {
-                                    opts.addError (formatMessage ("option \'" + opt.getName () + "\' does not accept fewer than " + cardinality [0] + " value(s)"));
-                                   
-                                    state = STATE_ERROR;
-                                }
-                                else
-                                    state = STATE_OPT;
-                            }
-                            else
-                            {
-                                if (valueCount < cardinality [1])
-                                {
-                                    ++ valueCount;
-                                    ++ a;
-                                    opt.addValue (value);
-                                }
-                                else
-                                {
-                                    // this check is redundant:
-//                                    if (valueCount < cardinality [0])
-//                                    {
-//                                        opts.addError (formatMessage ("option \'" + opt.getName () + "\' does not accept fewer than " + cardinality [0] + " value(s)"));
-//                                       
-//                                        state = STATE_ERROR;
-//                                    }
-//                                    else
-                                        state = STATE_FREE_ARGS;
-                                } 
-                            }
-                        }
-                        
-                        value = null;
-                    }
-                    break;
-                    
-                    
-                    case STATE_FREE_ARGS:
-                    {
-                        if (isOpt (args [a], valueCount, optdef))
-                        {
-                            state = STATE_OPT;
-                        }
-                        else
-                        {
-                            opts.setFreeArgs (args, a);
-                            break scan;
-                        }
-                    }
-                    break;
-                    
-                    
-                    case STATE_ERROR:
-                    {
-                        break scan; // TODO: could use the current value of 'a' for a better error message
-                    }
-                    
-                } // end of switch
-            }
-            
-            if (a == args.length)
-            {
-                if (opt != null) // validate the last option's min cardinality
-                {
-                    final int [] cardinality = optdef.getValueCardinality ();
-                    
-                    if (valueCount < cardinality [0])
-                    {
-                        opts.addError (formatMessage ("option \'" + opt.getName () + "\' does not accept fewer than " + cardinality [0] + " value(s)"));
-                    }
-                }
-                else
-                {
-                    opts.setFreeArgs (args, a);
-                }
-            }
-            
-        } // end of 'args' parsing
-        
-        
-        final IOpt [] specified = opts.getOpts ();
-        if (specified != null)
-        {
-            // validation: all required parameters must be specified
-            
-            final Set /* String(canonical name) */ required = new HashSet ();
-            required.addAll (m_metadata.getRequiredOpts ());
-            
-            for (int s = 0; s < specified.length; ++ s)
-            {
-                required.remove (specified [s].getCanonicalName ());
-            }
-            
-            if (! required.isEmpty ())
-            {
-                for (Iterator i = required.iterator (); i.hasNext (); )
-                {
-                    opts.addError (formatMessage ("missing required option \'" + (String) i.next () + "\'"));
-                }
-            }
-            
-            for (int s = 0; s < specified.length; ++ s)
-            {
-                final IOpt opt = specified [s];
-                final OptDef optdef = m_metadata.getOptDef (opt.getCanonicalName (), null); 
-                
-//                // validation: value cardinality constraints
-//                
-//                final int [] cardinality = optdef.getValueCardinality ();
-//                if (opt.getValueCount () < cardinality [0])
-//                    opts.addError (formatMessage ("option \'" + opt.getName () + "\' must have at least " + cardinality [0] +  " value(s)"));
-//                else if (opt.getValueCount () > cardinality [1])
-//                    opts.addError (formatMessage ("option \'" + opt.getName () + "\' must not have more than " + cardinality [1] +  " value(s)"));
-                
-                // validation: "requires" constraints
-                
-                final String [] requires = optdef.getRequiresSet (); // not canonicalized
-                if (requires != null)
-                {
-                    for (int r = 0; r < requires.length; ++ r)
-                    {
-                        if (opts.getOpt (requires [r]) == null)
-                            opts.addError (formatMessage ("option \'" + opt.getName () + "\' requires option \'" + requires [r] +  "\'"));
-                    }
-                }
-                
-                // validation: "not with" constraints
-                
-                final String [] excludes = optdef.getExcludesSet (); // not canonicalized
-                if (excludes != null)
-                {
-                    for (int x = 0; x < excludes.length; ++ x)
-                    {
-                        final Opt xopt = opts.getOpt (excludes [x]);
-                        if (xopt != null)
-                            opts.addError (formatMessage ("option \'" + opt.getName () + "\' cannot be used with option \'" + xopt.getName () +  "\'"));
-                    }
-                }
-                
-                // side effect: determine if usage is requested
-                
-                if (optdef.isUsage ())
-                {
-                    opts.setUsageRequested (opt.getName ().equals (opt.getCanonicalName ()) ? SHORT_USAGE : DETAILED_USAGE);
-                }
-            }
-        }
-        
-        return opts;
-    }
-    
-    private static String getOptCanonicalName (final String n, final OptDef optdef)
-    {
-        if (optdef.isPattern ())
-        {
-            final String canonicalPattern = optdef.getCanonicalName ();
-            final String [] patterns = optdef.getNames ();
-            
-            for (int p = 0; p < patterns.length; ++ p)
-            {
-                final String pattern = patterns [p];
-                
-                if (n.startsWith (pattern))
-                {
-                    return canonicalPattern.concat (n.substring (pattern.length ()));
-                }
-            }
-            
-            // this should never happen:
-            throw new IllegalStateException ("failed to detect pattern prefix for [" + n + "]");
-        }
-        else
-        {
-            return optdef.getCanonicalName ();
-        }
-    }
-    
-    /*
-     * ['optdef' can be null if no current opt def context has been established]
-     * 
-     * pre: av != null
-     * input not validated
-     */
-    private static boolean isOpt (final String av, final int valueCount, final OptDef optdef)
-    {
-        if (optdef != null)
-        {
-            // if the current optdef calls for more values, consume the next token
-            // as an op value greedily, without looking at its prefix:
-        
-            final int [] cardinality = optdef.getValueCardinality ();
-        
-            if (valueCount < cardinality [1]) return false;
-        }
-        
-        // else check av's prefix:
-        
-        for (int p = 0; p < OPT_PREFIXES.length; ++ p)
-        {
-            if (av.startsWith (OPT_PREFIXES [p]))
-                return (av.length () > OPT_PREFIXES [p].length ());
-        }
-        
-        return false;
-    }
-
-    /*
-     * pre: av != null and isOpt(av)=true
-     * input not validated
-     */
-    private static void getOptNameAndValue (final String av, final String [] nv)
-    {
-        nv [0] = null;
-        nv [1] = null;
-        
-        for (int p = 0; p < OPT_PREFIXES.length; ++ p)
-        {
-            if ((av.startsWith (OPT_PREFIXES [p])) && (av.length () > OPT_PREFIXES [p].length ()))
-            {
-                final String name = av.substring (OPT_PREFIXES [p].length ()); // with a possible value after a separator
-                
-                char separator = 0;
-                int sindex = Integer.MAX_VALUE;
-                
-                for (int s = 0; s < OPT_VALUE_SEPARATORS.length; ++ s)
-                {
-                    final int index = name.indexOf (OPT_VALUE_SEPARATORS [s]);
-                    if ((index > 0) && (index < sindex))
-                    {
-                        separator = OPT_VALUE_SEPARATORS [s];
-                        sindex = index;
-                    }
-                }
-                
-                if (separator != 0)
-                {
-                    nv [0] = name.substring (0, sindex);
-                    nv [1] = name.substring (sindex + 1);
-                }
-                else
-                {
-                    nv [0] = name;
-                }
-                
-                return;
-            }
-        }
-    }
-    
-    // protected: .............................................................   
-
-    // package: ...............................................................
-
-
-    static final class Opt implements IOptsParser.IOpt
-    {
-        public String getName ()
-        {
-            return m_name;
-        }
-        
-        public String getCanonicalName ()
-        {
-            return m_canonicalName;
-        }
-        
-        public int getValueCount ()
-        {
-            if (m_values == null) return 0;
-            
-            return m_values.size ();
-        }
-
-        public String getFirstValue ()
-        {
-            if (m_values == null) return null;
-            
-            return (String) m_values.get (0);
-        }
-
-        public String [] getValues ()
-        {
-            if (m_values == null) return IConstants.EMPTY_STRING_ARRAY;
-            
-            final String [] result = new String [m_values.size ()];
-            m_values.toArray (result);
-            
-            return result; 
-        }
-        
-        public String getPatternPrefix ()
-        {
-            return m_patternPrefix;
-        }
-        
-        public String toString ()
-        {
-            final StringBuffer s = new StringBuffer (m_name);
-            if (! m_canonicalName.equals (m_name)) s.append (" [" + m_canonicalName + "]");
-            
-            if (m_values != null)
-            {
-                s.append (": ");
-                s.append (m_values);
-            }
-            
-            return s.toString (); 
-        } 
-        
-        Opt (final String name, final String canonicalName, final String patternPrefix)
-        {
-            m_name = name;
-            m_canonicalName = canonicalName;
-            m_patternPrefix = patternPrefix;
-        }
-        
-        void addValue (final String value)
-        {
-            if (value == null) throw new IllegalArgumentException ("null input: value");
-            
-            if (m_values == null) m_values = new ArrayList ();
-            m_values.add (value);
-        }
-        
-        
-        private final String m_name, m_canonicalName, m_patternPrefix;
-        private ArrayList m_values; 
-
-    } // end of nested class
-    
-    
-    static final class Opts implements IOptsParser.IOpts
-    {
-        public int usageRequestLevel ()
-        {
-            return m_usageRequestLevel; 
-        }
-        
-        public void error (final PrintWriter out, final int width)
-        {
-            // TODO: use width
-            if (hasErrors ())
-            {
-                for (Iterator i = m_errors.iterator (); i.hasNext (); )
-                {
-                    out.println (i.next ());
-                }
-            } 
-        }
-
-        public String [] getFreeArgs ()
-        {
-            if (hasErrors ())
-                throw new IllegalStateException (errorsToString ());
-            
-            return m_freeArgs;
-        }
-
-        public IOpt [] getOpts ()
-        {
-            if (hasErrors ()) return null;
-            
-            if (m_opts.isEmpty ())
-                return EMPTY_OPT_ARRAY;
-            else
-            {
-                final IOpt [] result = new IOpt [m_opts.size ()];
-                m_opts.toArray (result);
-                
-                return result; 
-            }
-        }
-        
-        public IOpt [] getOpts (final String pattern)
-        {
-            if (hasErrors ()) return null;
-            
-            final List /* Opt */ patternOpts = (List) m_patternMap.get (pattern);
-            
-            if ((patternOpts == null) || patternOpts.isEmpty ())
-                return EMPTY_OPT_ARRAY;
-            else
-            {
-                final IOpt [] result = new IOpt [patternOpts.size ()];
-                patternOpts.toArray (result);
-                
-                return result;
-            }
-        }
-
-
-        public boolean hasArg (final String name)
-        {
-            if (hasErrors ())
-                throw new IllegalStateException (errorsToString ());
-            
-            return m_nameMap.containsKey (name);
-        }
-        
-        Opts ()
-        {
-            m_opts = new ArrayList ();
-            m_nameMap = new HashMap ();
-            m_patternMap = new HashMap ();
-        }
-        
-        void addOpt (final Opt opt, final OptDef optdef, final String occuranceName)
-        {
-            if (opt == null) throw new IllegalArgumentException ("null input: opt");
-            if (optdef == null) throw new IllegalArgumentException ("null input: optdef");
-            if (occuranceName == null) throw new IllegalArgumentException ("null input: occuranceName");
-            
-            // [name collisions detected elsewhere]
-            
-            m_opts.add (opt);
-            
-            final String [] names = optdef.getNames ();
-            final boolean isPattern = (opt.getPatternPrefix () != null);
-            
-            if (isPattern)
-            {
-                final String unprefixedName = occuranceName.substring (opt.getPatternPrefix ().length ());
-                
-                for (int n = 0; n < names.length; ++ n)
-                {
-                    m_nameMap.put (names [n].concat (unprefixedName), opt);
-                }
-                
-                {
-                    final String canonicalPattern = optdef.getCanonicalName ();
-                
-                    List patternList = (List) m_patternMap.get (canonicalPattern);
-                    if (patternList == null)
-                    {
-                        patternList = new ArrayList ();
-                        for (int n = 0; n < names.length; ++ n)
-                        {
-                            m_patternMap.put (names [n], patternList);
-                        } 
-                    }
-                    
-                    patternList.add (opt);
-                }
-            }
-            else
-            {
-                for (int n = 0; n < names.length; ++ n)
-                {
-                    m_nameMap.put (names [n], opt);
-                }
-            }
-        }
-        
-        Opt getOpt (final String occuranceName)
-        {
-            if (occuranceName == null) throw new IllegalArgumentException ("null input: occuranceName");
-            
-            return (Opt) m_nameMap.get (occuranceName);
-        }
-        
-        void setFreeArgs (final String [] args, final int start)
-        {
-            if (args == null) throw new IllegalArgumentException ("null input: args");
-            if ((start < 0) || (start > args.length)) throw new IllegalArgumentException ("invalid start index: " + start);
-            
-            m_freeArgs = new String [args.length - start];
-            System.arraycopy (args, start, m_freeArgs, 0, m_freeArgs.length);
-        }
-        
-        void setUsageRequested (final int level)
-        {
-            m_usageRequestLevel = level;
-        }
-        
-        void addError (final String msg)
-        {
-            if (msg != null)
-            {
-                if (m_errors == null) m_errors = new ArrayList ();
-                
-                m_errors.add (msg);
-            }
-        }
-        
-        boolean hasErrors ()
-        {
-            return (m_errors != null) && ! m_errors.isEmpty ();
-        }
-        
-        String errorsToString ()
-        {
-            if (! hasErrors ()) return "<no errors>";
-            
-            final CharArrayWriter caw = new CharArrayWriter ();
-            final PrintWriter pw = new PrintWriter (caw);
-            
-            error (pw, DEFAULT_ERROR_WIDTH);
-            pw.flush ();
-            
-            return caw.toString (); 
-        }
-        
-        
-        private final List /* Opt */ m_opts;
-        private final Map /* String(name/pattern-prefixed name)->Opt */ m_nameMap;
-        private final Map /* String(pattern prefix)->List<Opt> */ m_patternMap;
-        private String [] m_freeArgs;
-        private List /* String */ m_errors;
-        private int m_usageRequestLevel;
-        
-        private static final int DEFAULT_ERROR_WIDTH = 80;
-        private static final IOpt [] EMPTY_OPT_ARRAY = new IOpt [0]; 
-
-    } // end of nested class
-
-
-    static final class OptDef // TODO: merge with Opt?
-    {
-        OptDef (final boolean usage)
-        {
-            m_usage = usage;
-        }
-        
-        boolean isUsage ()
-        {
-            return m_usage;
-        }
-        
-        String getCanonicalName ()
-        {
-            return m_names [0];
-        }
-        
-        String [] getNames ()
-        {
-            return m_names;
-        }
-        
-        boolean isRequired ()
-        {
-            return m_required;
-        }
-        
-        String getValueMnemonic ()
-        {
-            return m_valueMnemonic;
-        }
-        
-        boolean isMergeable ()
-        {
-            return m_mergeable;
-        }
-        
-        boolean isDetailedOnly ()
-        {
-            return m_detailedOnly;
-        }
-        
-        boolean isPattern ()
-        {
-            return m_pattern;
-        }
-        
-        int [] getValueCardinality ()
-        {
-            return m_valueCardinality;
-        }
-        
-        String [] getRequiresSet ()
-        {
-            return m_requiresSet;
-        }
-        
-        String [] getExcludesSet ()
-        {
-            return m_excludesSet;
-        }
-        
-        String getDescription ()
-        {
-            return m_description;
-        }
-        
-        void setNames (final String [] names)
-        {
-            if (names == null) throw new IllegalArgumentException ("null input: names");
-            
-            m_names = names;
-        }
-        
-        void setRequired (final boolean required)
-        {
-            m_required = required;
-        }
-        
-        void setValueMnemonic (final String mnemonic)
-        {
-            if (mnemonic == null) throw new IllegalArgumentException ("null input: mnemonic");
-            
-            m_valueMnemonic = mnemonic;
-        }
-        
-        void setMergeable (final boolean mergeable)
-        {
-            m_mergeable = mergeable;
-        }
-        
-        void setDetailedOnly (final boolean detailedOnly)
-        {
-            m_detailedOnly = detailedOnly;
-        }
-        
-        void setPattern (final boolean pattern)
-        {
-            m_pattern = pattern;
-        }
-        
-        void setValueCardinality (final int [] cardinality)
-        {
-            if ((cardinality == null) || (cardinality.length != 2)) throw new IllegalArgumentException ("null or invalid input: cardinality");
-            
-            m_valueCardinality = cardinality;
-        }
-        
-        void setRequiresSet (final String [] names)
-        {
-            if (names == null) throw new IllegalArgumentException ("null input: names"); 
-            
-            m_requiresSet = names.length > 0 ? names : null;
-        }
-        
-        void setExcludesSet (final String [] names)
-        {
-            if (names == null) throw new IllegalArgumentException ("null input: names");
-            
-            m_excludesSet = names.length > 0 ? names : null;
-        }
-        
-        void setDescription (final String description)
-        {
-            if (description == null) throw new IllegalArgumentException ("null input: description");
-            
-            m_description = description;
-        }
-        
-        
-        static final int [] C_ZERO = new int [] {0, 0};
-        static final int [] C_ONE = new int [] {1, 1};
-        static final int [] C_ZERO_OR_ONE = new int [] {0, 1};
-        static final int [] C_ZERO_OR_MORE = new int [] {0, Integer.MAX_VALUE};
-        static final int [] C_ONE_OR_MORE = new int [] {1, Integer.MAX_VALUE};
-        
-        
-        private final boolean m_usage;
-        private String [] m_names;
-        private boolean m_required;
-        private String m_valueMnemonic;
-        private boolean m_mergeable;
-        private boolean m_detailedOnly;
-        private boolean m_pattern;
-        private int [] m_valueCardinality;
-        private String [] m_requiresSet, m_excludesSet;
-        private String m_description;
-        
-    } // end of nested class
-    
-    
-    static final class OptDefMetadata
-    {
-        OptDefMetadata ()
-        {
-            m_optdefs = new ArrayList ();
-            m_optdefMap = new HashMap ();
-            m_requiredOpts = new HashSet ();
-            m_patternOptDefMap = new HashMap ();
-        }
-        
-        OptDef getOptDef (final String name, final String [] prefixout)
-        {
-            if (name == null) throw new IllegalArgumentException ("null input: name");
-            
-            if (prefixout != null) prefixout [0] = null;
-            
-            // first, see if this is a regular option:
-            OptDef result = (OptDef) m_optdefMap.get (name);
-            
-            // next, see if this is a prefixed option:
-            if (result == null)
-            {
-                for (Iterator ps = m_patternOptDefMap.entrySet ().iterator ();
-                     ps.hasNext (); )
-                {
-                    final Map.Entry entry = (Map.Entry) ps.next ();
-                    final String pattern = (String) entry.getKey ();
-                    
-                    if (name.startsWith (pattern))
-                    {
-                        if (prefixout != null) prefixout [0] = pattern;
-                        result = (OptDef) entry.getValue ();
-                        break;
-                    }
-                }
-            }
-            
-            return result;
-        }
-        
-        Iterator /* OptDef */ getOptDefs ()
-        {
-            return m_optdefs.iterator ();
-        }
-        
-        OptDef getPatternOptDefs (final String pattern) // returns null if no such pattern is defined
-        {
-            if (pattern == null) throw new IllegalArgumentException ("null input: pattern");
-            
-            return (OptDef) m_patternOptDefMap.get (pattern);
-        }
-        
-        Set /* String(canonical name) */ getRequiredOpts ()
-        {
-            return m_requiredOpts;
-        }
-        
-        OptDef getUsageOptDef ()
-        {
-            return m_usageOptDef;
-        }
-        
-        void addOptDef (final OptDef optdef)
-        {
-            if (optdef == null) throw new IllegalArgumentException ("null input: optdef");
-            
-            final Map map = optdef.isPattern () ? m_patternOptDefMap : m_optdefMap;
-            final String [] names = optdef.getNames ();
-            
-            for (int n = 0; n < names.length; ++ n)
-            {
-                if (map.containsKey (names [n]))
-                    throw new IllegalArgumentException ("duplicate option name [" + names [n] + "]");
-                    
-                map.put (names [n], optdef);
-            }
-            
-            m_optdefs.add (optdef);
-            
-            if (optdef.isRequired ())
-                m_requiredOpts.add (optdef.getCanonicalName ());
-            
-            if (optdef.isUsage ())
-            {
-                if (m_usageOptDef != null)
-                    throw new IllegalArgumentException ("usage optdef set already");
-                    
-                m_usageOptDef = optdef;
-            }
-        }
-        
-        
-        final List /* OptDef */ m_optdefs; // keeps the addition order
-        final Map /* String(name)->OptDef */ m_optdefMap;
-        final Set /* String(canonical name) */ m_requiredOpts;
-        final Map /* String(pattern name)->OptDef */ m_patternOptDefMap;
-        private OptDef m_usageOptDef; 
-        
-    } // end of nested class
-
-  
-    static final class MetadataParser
-    {
-        /*
-         * metadata := ( optdef )* <EOF>
-         * 
-         * optdef := optnamelist ":" optmetadata ";"
-         * optnamelist := namelist
-         * optmetadata :=
-         *      ("optional" | "required" )
-         *      [ "," "mergeable" ]
-         *      [ "," "detailedonly" ]
-         *      [ "," "pattern" ] 
-         *      "," "values" ":" cardinality
-         *      [ "," name ]
-         *      [ "," "requires" "{" namelist "}" ]
-         *      [ "," "notwith" "{" namelist "}" ]
-         *      "," text
-         * cardinality := "0" | "1" | "?"
-         * namelist := name ( "," name )*
-         * name := <single quoted string>  
-         * text := <double quoted string> 
-         */         
-         OptDef [] parse (final Reader in)
-         {
-             if (in == null) throw new IllegalArgumentException ("null input: in");             
-             m_in = in;
-             
-             nextChar ();
-             nextToken ();
-             
-             while (m_token != Token.EOF)
-             {
-                 if (m_opts == null) m_opts = new ArrayList ();
-                 m_opts.add (optdef ());
-             }
-             
-             final OptDef [] result;
-             
-             if ((m_opts == null) || (m_opts.size () == 0))
-                result = EMPTY_OPTDEF_ARRAY;
-             else
-             {
-                 result = new OptDef [m_opts.size ()];
-                 m_opts.toArray (result);
-             }
-             
-             m_in = null;
-             m_opts = null;
-             
-             return result;
-         }
-         
-         OptDef optdef ()
-         {
-             final OptDef optdef = new OptDef (false); 
-             
-             optdef.setNames (optnamelist ());
-             accept (Token.COLON_ID);
-             optmetadata (optdef);
-             accept (Token.SEMICOLON_ID);
-             
-             return optdef;
-         }
-         
-         String [] optnamelist ()
-         {
-             return namelist ();
-         }
-         
-         void optmetadata (final OptDef optdef)
-         {
-             switch (m_token.getID ())
-             {
-                 case Token.REQUIRED_ID:
-                 {
-                     accept ();
-                     optdef.setRequired (true);
-                 }
-                 break;
-                 
-                 case Token.OPTIONAL_ID:
-                 {
-                     accept ();
-                     optdef.setRequired (false);
-                 }
-                 break;
-                 
-                 default:
-                    throw new IllegalArgumentException ("parse error: invalid token " + m_token + ", expected " + Token.REQUIRED + " or " + Token.OPTIONAL);
-                 
-             } // end of switch
-             
-             accept (Token.COMMA_ID);
-             
-             if (m_token.getID () == Token.MERGEABLE_ID)
-             {
-                 accept ();
-                 optdef.setMergeable (true);
-                 
-                 accept (Token.COMMA_ID);
-             }
-             
-             if (m_token.getID () == Token.DETAILEDONLY_ID)
-             {
-                 accept ();
-                 optdef.setDetailedOnly (true);
-                 
-                 accept (Token.COMMA_ID);
-             }
-             
-             if (m_token.getID () == Token.PATTERN_ID)
-             {
-                 accept ();
-                 optdef.setPattern (true);
-                 
-                 accept (Token.COMMA_ID);
-             }
-             
-             accept (Token.VALUES_ID);
-             accept (Token.COLON_ID);
-             optdef.setValueCardinality (cardinality ());
-             
-             accept (Token.COMMA_ID);
-             if (m_token.getID () == Token.STRING_ID)
-             {
-                 optdef.setValueMnemonic (m_token.getValue ());
-                 accept ();
-                 
-                 accept (Token.COMMA_ID);
-             }
-             
-             if (m_token.getID () == Token.REQUIRES_ID)
-             {
-                 accept ();
-                 
-                 accept (Token.LBRACKET_ID);
-                 optdef.setRequiresSet (namelist ());
-                 accept (Token.RBRACKET_ID);
-                 
-                 accept (Token.COMMA_ID);
-             }
-             
-             if (m_token.getID () == Token.EXCLUDES_ID)
-             {
-                 accept ();
-                 
-                 accept (Token.LBRACKET_ID);
-                 optdef.setExcludesSet (namelist ());
-                 accept (Token.RBRACKET_ID);
-                 
-                 accept (Token.COMMA_ID);
-             }
-             
-             optdef.setDescription (accept (Token.TEXT_ID).getValue ());
-         }
-         
-         int [] cardinality ()
-         {
-             final Token result = accept (Token.CARD_ID);
-             
-             if ("0".equals (result.getValue ()))
-                return OptDef.C_ZERO;
-             else if ("1".equals (result.getValue ()))
-                return OptDef.C_ONE;
-             else // ?
-                return OptDef.C_ZERO_OR_ONE;
-         }
-         
-         String [] namelist ()
-         {
-             final List _result = new ArrayList ();
-             
-             _result.add (accept (Token.STRING_ID).getValue ());
-             while (m_token.getID () == Token.COMMA_ID)
-             {
-                 accept ();
-                 _result.add (accept (Token.STRING_ID).getValue ());
-             }
-             
-             final String [] result = new String [_result.size ()];
-             _result.toArray (result);
-             
-             return result;
-         }
-         
-         
-         Token accept ()
-         {
-             final Token current = m_token;
-             nextToken ();
-             
-             return current;
-         }
-         
-         Token accept (final int tokenID)
-         {
-             final Token current = m_token;
-             
-             if (m_token.getID () == tokenID)
-                nextToken ();
-             else
-                throw new IllegalArgumentException ("parse error: invalid token [" + m_token + "], expected type [" + tokenID + "]");
-                
-             return current;
-         }
-         
-         // "scanner":
-         
-         void nextToken ()
-         {
-             consumeWS ();
-             
-             switch (m_currentChar)
-             {
-                 case -1: m_token = Token.EOF; break;
-                 
-                 case ':':
-                 {
-                     nextChar ();
-                     m_token = Token.COLON;
-                 }
-                 break;
-                 
-                 case ';':
-                 {
-                     nextChar ();
-                     m_token = Token.SEMICOLON;
-                 }
-                 break;
-                 
-                 case ',':
-                 {
-                     nextChar ();
-                     m_token = Token.COMMA;
-                 }
-                 break;
-                 
-                 case '{':
-                 {
-                     nextChar ();
-                     m_token = Token.LBRACKET;
-                 }
-                 break;
-                 
-                 case '}':
-                 {
-                     nextChar ();
-                     m_token = Token.RBRACKET;
-                 }
-                 break;
-                 
-                 case '0':
-                 {
-                     nextChar ();
-                     m_token = new Token (Token.CARD_ID, "0");
-                 }
-                 break;
-                 
-                 case '1':
-                 {
-                     nextChar ();
-                     m_token = new Token (Token.CARD_ID, "1");
-                 }
-                 break;
-                 
-                 case '?':
-                 {
-                     nextChar ();
-                     m_token = new Token (Token.CARD_ID, "?");
-                 }
-                 break;
-                                 
-                 case '\'':
-                 {
-                     final StringBuffer value = new StringBuffer ();
-                     
-                     nextChar ();
-                     while (m_currentChar != '\'')
-                     {
-                         value.append ((char) m_currentChar);
-                         nextChar ();
-                     }
-                     nextChar ();
-                     
-                     m_token = new Token (Token.STRING_ID, value.toString ());
-                 }
-                 break;
-                 
-                 case '\"':
-                 {
-                     final StringBuffer value = new StringBuffer ();
-                     
-                     nextChar ();
-                     while (m_currentChar != '\"')
-                     {
-                         value.append ((char) m_currentChar);
-                         nextChar ();
-                     }
-                     nextChar ();
-                     
-                     m_token = new Token (Token.TEXT_ID, value.toString ());
-                 }
-                 break;
-                 
-                 default:
-                 {
-                     final StringBuffer value = new StringBuffer ();
-                     
-                     while (Character.isLetter ((char) m_currentChar))
-                     {
-                         value.append ((char) m_currentChar);
-                         nextChar ();
-                     }
-                     
-                     final Token token = (Token) KEYWORDS.get (value.toString ());
-                     if (token == null)
-                        throw new IllegalArgumentException ("parse error: unrecognized keyword [" + value  + "]");
-                     
-                     m_token = token;
-                 }
-                                  
-             } // end of switch
-         }
-         
-         
-         private void consumeWS ()
-         {
-             if (m_currentChar == -1)
-                return;
-             else
-             {
-                 while (Character.isWhitespace ((char) m_currentChar))
-                 {
-                    nextChar ();
-                 }
-             }
-
-             // TODO: #-comments
-         }
-         
-         private void nextChar ()
-         {
-             try
-             {
-                m_currentChar = m_in.read ();
-             }
-             catch (IOException ioe)
-             {
-                 throw new RuntimeException ("I/O error while parsing: " + ioe); 
-             }
-         }
-         
-         
-         private Reader m_in;
-         private List m_opts;
-         
-         private Token m_token;
-         private int m_currentChar;
-         
-         private static final Map KEYWORDS;
-         
-         private static final OptDef [] EMPTY_OPTDEF_ARRAY = new OptDef [0];
-         
-         static
-         {
-             KEYWORDS = new HashMap (17);
-             
-             KEYWORDS.put (Token.OPTIONAL.getValue (), Token.OPTIONAL);
-             KEYWORDS.put (Token.REQUIRED.getValue (), Token.REQUIRED);
-             KEYWORDS.put (Token.VALUES.getValue (), Token.VALUES);
-             KEYWORDS.put (Token.REQUIRES.getValue (), Token.REQUIRES);
-             KEYWORDS.put (Token.EXCLUDES.getValue (), Token.EXCLUDES);
-             KEYWORDS.put (Token.MERGEABLE.getValue (), Token.MERGEABLE);
-             KEYWORDS.put (Token.DETAILEDONLY.getValue (), Token.DETAILEDONLY);
-             KEYWORDS.put (Token.PATTERN.getValue (), Token.PATTERN);
-         }
-        
-    } // end of nested class
-    
-    
-    OptsParser (final String metadataResourceName, final ClassLoader loader, final String [] usageOpts)
-    {
-        this (metadataResourceName, loader, null, usageOpts);
-    }
-    
-    OptsParser (final String metadataResourceName, final ClassLoader loader, final String msgPrefix, final String [] usageOpts)
-    {
-        if (metadataResourceName == null) throw new IllegalArgumentException ("null input: metadataResourceName");
-        
-        m_msgPrefix = msgPrefix;
-        
-        InputStream in = null;
-        try
-        {
-            in = ResourceLoader.getResourceAsStream (metadataResourceName, loader);
-            if (in == null)
-                throw new IllegalArgumentException ("resource [" + metadataResourceName + "] could not be loaded via [" + loader + "]");
-            
-            // TODO: encoding
-            final Reader rin = new InputStreamReader (in);
-            
-            m_metadata = parseOptDefMetadata (rin, usageOpts);   
-        }
-        finally
-        {
-            if (in != null) try { in.close (); } catch (IOException ignore) {} 
-        }
-    }
-    
-    // private: ...............................................................
-
-
-    private static final class Token
-    {
-        Token (final int ID, final String value)
-        {
-            if (value == null) throw new IllegalArgumentException ("null input: value");
-            
-            m_ID = ID;
-            m_value = value;
-        }
-        
-        int getID ()
-        {
-            return m_ID;
-        }
-        
-        String getValue ()
-        {
-            return m_value;
-        }
-        
-        public String toString ()
-        {
-            return m_ID + ": [" + m_value + "]";
-        }
-        
-        
-        static final int EOF_ID = 0;
-        static final int STRING_ID = 1;
-        static final int COLON_ID = 2;
-        static final int SEMICOLON_ID = 3;
-        static final int COMMA_ID = 4;
-        static final int LBRACKET_ID = 5;
-        static final int RBRACKET_ID = 6;
-        static final int OPTIONAL_ID = 7;
-        static final int REQUIRED_ID = 8;
-        static final int CARD_ID = 9;
-        static final int VALUES_ID = 10;
-        static final int TEXT_ID = 11;
-        static final int REQUIRES_ID = 12;
-        static final int EXCLUDES_ID = 13;
-        static final int MERGEABLE_ID = 14;
-        static final int DETAILEDONLY_ID = 15;
-        static final int PATTERN_ID = 16;
-        
-        static final Token EOF = new Token (EOF_ID, "<EOF>");
-        static final Token COLON = new Token (COLON_ID, ":");
-        static final Token SEMICOLON = new Token (SEMICOLON_ID, ";");
-        static final Token COMMA = new Token (COMMA_ID, ",");
-        static final Token LBRACKET = new Token (LBRACKET_ID, "{");
-        static final Token RBRACKET = new Token (RBRACKET_ID, "}");
-        static final Token OPTIONAL = new Token (OPTIONAL_ID, "optional");
-        static final Token REQUIRED = new Token (REQUIRED_ID, "required");
-        static final Token VALUES = new Token (VALUES_ID, "values");
-        static final Token REQUIRES = new Token (REQUIRES_ID, "requires");
-        static final Token EXCLUDES = new Token (EXCLUDES_ID, "excludes");
-        static final Token MERGEABLE = new Token (MERGEABLE_ID, "mergeable");
-        static final Token DETAILEDONLY = new Token (DETAILEDONLY_ID, "detailedonly");
-        static final Token PATTERN = new Token (PATTERN_ID, "pattern");
-        
-        private final int m_ID;
-        private final String m_value;
-        
-    } // end of nested class
-    
-    
-    private static OptDefMetadata parseOptDefMetadata (final Reader in, final String [] usageOpts)
-    {
-        final MetadataParser parser = new MetadataParser ();
-        final OptDef [] optdefs = parser.parse (in);
-        
-        // validate:
-        
-//        for (int o = 0; o < optdefs.length; ++ o)
-//        {
-//            final OptDef optdef = optdefs [o];
-//            final int [] cardinality = optdef.getValueCardinality ();
-//            
-//            if (optdef.isMergeable ())
-//            {
-//                if ((cardinality [1] != 0) && (cardinality [1] != Integer.MAX_VALUE))
-//                    throw new IllegalArgumentException ("option [" + optdef.getCanonicalName () + "] is mergeable and can only specify {0, +inf} for max value cardinality: " + cardinality [1]); 
-//            }            
-//        } 
-         
-        final OptDefMetadata result = new OptDefMetadata ();
-        for (int o = 0; o < optdefs.length; ++ o)
-        {
-            result.addOptDef (optdefs [o]);
-        }
-        
-        // add usage opts:
-        if (usageOpts != null)
-        {
-            final OptDef usage = new OptDef (true);
-            
-            usage.setNames (usageOpts);
-            usage.setDescription ("display usage information");
-            usage.setValueCardinality (OptDef.C_ZERO);
-            usage.setRequired (false);
-            usage.setDetailedOnly (false);
-            usage.setMergeable (false);
-            
-            result.addOptDef (usage);
-        }
-        
-        // TODO: fix this to be pattern-savvy
-        
-        for (int o = 0; o < optdefs.length; ++ o)
-        {
-            final OptDef optdef = optdefs [o];
-            
-            final String [] requires = optdef.getRequiresSet ();
-            if (requires != null)
-            {
-                for (int r = 0; r < requires.length; ++ r)
-                {
-                    final OptDef ropt = result.getOptDef (requires [r], null);
-                    if (ropt == null)
-                        throw new IllegalArgumentException ("option [" + optdef.getCanonicalName () + "] specifies an unknown option [" + requires [r] + "] in its \'requires\' set");
-                    
-                    if (ropt == optdef)
-                        throw new IllegalArgumentException ("option [" + optdef.getCanonicalName () + "] specifies itself in its \'requires\' set");
-                }
-            }
-            
-            final String [] excludes = optdef.getExcludesSet ();
-            if (excludes != null)
-            {
-                for (int x = 0; x < excludes.length; ++ x)
-                {
-                    final OptDef xopt = result.getOptDef (excludes [x], null);
-                    if (xopt == null)
-                        throw new IllegalArgumentException ("option [" + optdef.getCanonicalName () + "] specifies an unknown option [" + excludes [x] + "] in its \'excludes\' set");
-                    
-                    if (xopt.isRequired ())
-                        throw new IllegalArgumentException ("option [" + optdef.getCanonicalName () + "] specifies a required option [" + excludes [x] + "] in its \'excludes\' set");
-                    
-                    if (xopt == optdef)
-                        throw new IllegalArgumentException ("option [" + optdef.getCanonicalName () + "] specifies itself in its \'excludes\' set");
-                }
-            }
-        }
-        
-        return result;
-    }
-    
-    private String formatMessage (final String msg)
-    {
-        if (m_msgPrefix == null) return msg;
-        else
-        {
-            return m_msgPrefix.concat (msg);
-        }
-    }
-    
-    
-    private final String m_msgPrefix;
-    private final OptDefMetadata m_metadata;
-    
-    private static final int CANONICAL_OPT_PREFIX = 1; // indexes into OPT_PREFIXES
-    private static final String [] OPT_PREFIXES = new String [] {"--", "-"}; // HACK: these must appear in decreasing length order
-    private static final char [] OPT_VALUE_SEPARATORS = new char [] {':', '='};
-    
-    private static final int STATE_OPT = 0, STATE_OPT_VALUE = 1, STATE_FREE_ARGS = 2, STATE_ERROR = 3;
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/asserts/$assert.java b/core/java12/com/vladium/util/asserts/$assert.java
deleted file mode 100644
index 9160f08..0000000
--- a/core/java12/com/vladium/util/asserts/$assert.java
+++ /dev/null
@@ -1,60 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: \044assert.java,v 1.1.1.1 2004/05/09 16:57:57 vlad_r Exp $
- */
-package com.vladium.util.asserts;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2001
- */
-public
-abstract class $assert
-{
-    // public: ................................................................
-    
-    
-    // TODO: set to false for release
-    
-    /**
-     * Global compile time assertion flag.
-     */
-    public static final boolean ENABLED = false;
-    
-    /**
-     * 
-     * @param condition
-     * @param msg
-     */
-    public static void ASSERT (final boolean condition, final String msg)
-    {
-        if (ENABLED)
-        {
-            if (! condition) throw new RuntimeException (msg);
-        }
-    }
-    
-    public static void ASSERT (final boolean condition)
-    {
-        if (ENABLED)
-        {
-            if (! condition) throw new RuntimeException ("ASSERTION FAILURE");
-        }
-    }
-    
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private $assert () {} // prevent subclassing
-
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/util/exception/AbstractException.java b/core/java12/com/vladium/util/exception/AbstractException.java
deleted file mode 100644
index ab6f9d6..0000000
--- a/core/java12/com/vladium/util/exception/AbstractException.java
+++ /dev/null
@@ -1,329 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AbstractException.java,v 1.1.1.1 2004/05/09 16:57:57 vlad_r Exp $
- */
-package com.vladium.util.exception;
-
-import java.io.IOException;
-import java.io.ObjectOutputStream;
-import java.io.PrintStream;
-import java.io.PrintWriter;
-
-// ----------------------------------------------------------------------------
-/**
- * Based on code published by me in <a href="http://www.fawcette.com/javapro/2002_12/online/exception_vroubtsov_12_16_02/default_pf.asp">JavaPro, 2002</a>.<P>
- * 
- * This checked exception class is designed as a base/expansion point for the
- * entire hierarchy of checked exceptions in a project.<P>
- * 
- * It provides the following features:
- * <UL>
- *    <LI> ability to take in compact error codes that map to full text messages
- *    in a resource bundle loaded at this class' instantiation time. This avoids
- *    hardcoding the error messages in product code and allows for easy
- *    localization of such text if required. Additionally, these messages
- *    can be parametrized in the java.text.MessageFormat style;
- *    <LI> exception chaining in J2SE versions prior to 1.4
- * </UL>
- * 
- * See {@link AbstractRuntimeException} for an unchecked version of the same class.<P> 
- *
- * TODO: javadoc
- *
- * Each constructor that accepts a String 'message' parameter accepts an error
- * code as well. You are then responsible for ensuring that either the root
- * <CODE>com.vladium.exception.exceptions</CODE> resource bundle
- * or your project/exception class-specific resource bundle [see
- * <A HREF="#details">below</A> for details] contains a mapping for this error
- * code. When this lookup fails the passed String value itself will be used as
- * the error message.<P>
- *
- * All constructors taking an 'arguments' parameter supply parameters to the error
- * message used as a java.text.MessageFormat pattern.<P>
- * 
- * Example:
- * <PRE><CODE>
- *  File file = ...
- *  try
- *  ...
- *  catch (Exception e)
- *  {
- *      throw new AbstractException ("FILE_NOT_FOUND", new Object[] {file, e}, e);
- *  }
- * </CODE></PRE>
- *      where <CODE>com.vladium.util.exception.exceptions</CODE> contains:
- * <PRE><CODE>
- * FILE_NOT_FOUND: file {0} could not be opened: {1}
- * </CODE></PRE>
- *
- * To log exception data use {@link #getMessage} or <CODE>printStackTrace</CODE>
- * family of methods. You should never have to use toString().<P>
- *
- * <A NAME="details"> It is also possible to use project- or exception
- * subhierarchy-specific message resource bundles without maintaining all error
- * codes in <CODE>com.vladium.exception.exceptions</CODE>. To do so, create a
- * custom resource bundle and add the following static initializer code to your
- * base exception class:
- * <PRE><CODE>
- *  static
- *  {
- *      addExceptionResource (MyException.class, "my_custom_resource_bundle");
- *  }
- * </CODE></PRE>
- * The bundle name is relative to MyException package. This step can omitted if
- * the bundle name is "exceptions".
- * 
- * Note that the implementation correctly resolves error code name collisions
- * across independently developed exception families, as long as resource bundles
- * use unique names. Specifically, error codes follow inheritance and hiding rules
- * similar to Java class static methods. See {@link ExceptionCommon#addExceptionResource}
- * for further details.
- *
- * @author Vlad Roubtsov, (C) 2002
- */
-public
-abstract class AbstractException extends Exception implements ICodedException, IThrowableWrapper
-{
-    // public: ................................................................
-
-    /**
-     * Constructs an exception with null message and null cause.
-     */    
-    public AbstractException ()
-    {
-        m_cause = null;
-        m_arguments = null;
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and null cause.
-     *
-     * @param message the detail message [can be null]
-     */
-    public AbstractException (final String message)
-    {
-        super (message);
-        m_cause = null;
-        m_arguments = null;
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and null cause.
-     *   
-     * @param message the detail message [can be null]
-     * @param arguments message format parameters [can be null or empty]
-     *
-     * @see java.text.MessageFormat
-     */
-    public AbstractException (final String message, final Object [] arguments)
-    {
-        super (message);
-        m_cause = null;
-        m_arguments = arguments == null ? null : (Object []) arguments.clone ();
-    }
-    
-    /**
-     * Constructs an exception with null error message/code and given cause.
-     *
-     * @param cause the cause [nested exception] [can be null]
-     */
-    public AbstractException (final Throwable cause)
-    {
-        super ();
-        m_cause = cause;
-        m_arguments = null;
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and given cause.
-     *
-     * @param message the detail message [can be null]
-     * @param cause the cause [nested exception] [can be null]
-     */
-    public AbstractException (final String message, final Throwable cause)
-    {
-        super (message);
-        m_cause = cause;
-        m_arguments = null;
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and given cause.
-     *
-     * @param message the detail message [can be null]
-     * @param arguments message format parameters [can be null or empty]
-     * @param cause the cause [nested exception] [can be null]
-     *
-     * @see java.text.MessageFormat
-     */
-    public AbstractException (final String message, final Object [] arguments, final Throwable cause)
-    {
-        super (message);
-        m_cause = cause;
-        m_arguments = arguments == null ? null : (Object []) arguments.clone ();
-    }
-    
-
-    /**
-     * Overrides base method to support error code lookup and avoid returning nulls.
-     * Note that this does not recurse into any 'cause' for message lookup, it only
-     * uses the data passed into the constructor. Subclasses cannot override.<P>
-     *
-     * Equivalent to {@link #getLocalizedMessage}.
-     *
-     * @return String error message provided at construction time or the result
-     * of toString() if no/null message was provided [never null].
-     */  
-    public final String getMessage ()
-    {
-        if (m_message == null) // not synchronized by design
-        {
-            String msg;
-            final String supermsg = super.getMessage ();
-            final Class _class = getClass ();
-            
-            if (m_arguments == null)
-            {
-                msg = ExceptionCommon.getMessage (_class, supermsg);
-            }
-            else
-            {
-                msg = ExceptionCommon.getMessage (_class, supermsg, m_arguments);
-            }
-            
-            if (msg == null)
-            {
-                // this is the same as what's done in Throwable.toString() [copied here to be independent of future JDK changes]
-                final String className = _class.getName ();
-                
-                msg = (supermsg != null) ? (className + ": " + supermsg) : className;
-            }
-            
-            m_message = msg;
-        }
-        
-        return m_message;
-    }
-    
-    /**
-     * Overrides base method for the sole purpose of making it final.<P>
-     * 
-     * Equivalent to {@link #getMessage}.
-     */
-    public final String getLocalizedMessage ()
-    {
-        // this is the same as what's done in Throwable
-        // [copied here to be independent of future JDK changes]
-        return getMessage ();
-    }
-
-    /**
-     * Overrides Exception.printStackTrace() to (a) force the output to go
-     * to System.out and (b) handle nested exceptions in JDKs prior to 1.4.<P>
-     * 
-     * Subclasses cannot override.
-     */    
-    public final void printStackTrace ()
-    {
-        // NOTE: unlike the JDK implementation, force the output to go to System.out:
-        ExceptionCommon.printStackTrace (this, System.out);
-    }
-    
-    /**
-     * Overrides Exception.printStackTrace() to handle nested exceptions in JDKs prior to 1.4.<P>
-     * 
-     * Subclasses cannot override.
-     */    
-    public final void printStackTrace (final PrintStream s)
-    {
-        ExceptionCommon.printStackTrace (this, s);
-    }
-    
-    /**
-     * Overrides Exception.printStackTrace() to handle nested exceptions in JDKs prior to 1.4.<P>
-     * 
-     * Subclasses cannot override.
-     */ 
-    public final void printStackTrace (final PrintWriter s)
-    {
-        ExceptionCommon.printStackTrace (this, s);
-    }
-
-    // ICodedException:
-    
-    /**
-     * Returns the String that was passed as 'message' constructor argument.
-     * Can be null.
-     *
-     * @return message code string [can be null]
-     */
-    public final String getErrorCode ()
-    {
-        return super.getMessage ();
-    }
-
-    // IThrowableWrapper:
-    
-    /**
-     * This implements {@link IThrowableWrapper}
-     * and also overrides the base method in JDK 1.4+.
-     */
-    public final Throwable getCause ()
-    {
-        return m_cause;
-    }
-
-    public void __printStackTrace (final PrintStream ps)
-    {
-        super.printStackTrace (ps);
-    }
-    
-    public void __printStackTrace (final PrintWriter pw)
-    {
-        super.printStackTrace (pw);
-    }
-
-    /**
-     * Equivalent to {@link ExceptionCommon#addExceptionResource}, repeated here for
-     * convenience. Subclasses should invoke from static initializers <I>only</I>.
-     * 'namespace' should be YourException.class.
-     */
-    public static void addExceptionResource (final Class namespace,
-                                             final String messageResourceBundleName)
-    {
-        // note: 'namespace' will be the most derived class; it is possible to
-        // auto-detect that in a static method but that requires some security
-        // permissions
-        ExceptionCommon.addExceptionResource (namespace, messageResourceBundleName);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-
-    /*
-     * Ensures that this instance can be serialized even if some message parameters
-     * are not serializable objects.
-     */
-    private void writeObject (final ObjectOutputStream out)
-        throws IOException
-    {
-        getMessage (); // transform this instance to serializable form
-        out.defaultWriteObject ();
-    }
-
-    
-    private String m_message; // marshalled/cached result of getMessage()
-    private transient final Object [] m_arguments;
-    // note: this field duplicates functionality available in stock Throwable in JRE 1.4+
-    private final Throwable m_cause;
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/util/exception/AbstractRuntimeException.java b/core/java12/com/vladium/util/exception/AbstractRuntimeException.java
deleted file mode 100644
index 66190d8..0000000
--- a/core/java12/com/vladium/util/exception/AbstractRuntimeException.java
+++ /dev/null
@@ -1,329 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: AbstractRuntimeException.java,v 1.1.1.1 2004/05/09 16:57:57 vlad_r Exp $
- */
-package com.vladium.util.exception;
-
-import java.io.IOException;
-import java.io.ObjectOutputStream;
-import java.io.PrintStream;
-import java.io.PrintWriter;
-
-// ----------------------------------------------------------------------------
-/**
- * Based on code published by me in <a href="http://www.fawcette.com/javapro/2002_12/online/exception_vroubtsov_12_16_02/default_pf.asp">JavaPro, 2002</a>.<P>
- * 
- * This unchecked exception class is designed as a base/expansion point for the
- * entire hierarchy of unchecked exceptions in a project.<P>
- * 
- * It provides the following features:
- * <UL>
- *    <LI> ability to take in compact error codes that map to full text messages
- *    in a resource bundle loaded at this class' instantiation time. This avoids
- *    hardcoding the error messages in product code and allows for easy
- *    localization of such text if required. Additionally, these messages
- *    can be parametrized in the java.text.MessageFormat style;
- *    <LI> exception chaining in J2SE versions prior to 1.4
- * </UL>
- * 
- * See {@link AbstractException} for a checked version of the same class.<P> 
- * 
- * TODO: javadoc
- *
- * Each constructor that accepts a String 'message' parameter accepts an error
- * code as well. You are then responsible for ensuring that either the root
- * <CODE>com.vladium.exception.exceptions</CODE> resource bundle
- * or your project/exception class-specific resource bundle [see
- * <A HREF="#details">below</A> for details] contains a mapping for this error
- * code. When this lookup fails the passed String value itself will be used as
- * the error message.<P>
- *
- * All constructors taking an 'arguments' parameter supply parameters to the error
- * message used as a java.text.MessageFormat pattern.<P>
- * 
- * Example:
- * <PRE><CODE>
- *  File file = ...
- *  try
- *  ...
- *  catch (Exception e)
- *  {
- *      throw new AbstractRuntimeException ("FILE_NOT_FOUND", new Object[] {file, e}, e);
- *  }
- * </CODE></PRE>
- *      where <CODE>com.vladium.util.exception.exceptions</CODE> contains:
- * <PRE><CODE>
- * FILE_NOT_FOUND: file {0} could not be opened: {1}
- * </CODE></PRE>
- *
- * To log exception data use {@link #getMessage} or <CODE>printStackTrace</CODE>
- * family of methods. You should never have to use toString().<P>
- *
- * <A NAME="details"> It is also possible to use project- or exception
- * subhierarchy-specific message resource bundles without maintaining all error
- * codes in <CODE>com.vladium.exception.exceptions</CODE>. To do so, create a
- * custom resource bundle and add the following static initializer code to your
- * base exception class:
- * <PRE><CODE>
- *  static
- *  {
- *      addExceptionResource (MyException.class, "my_custom_resource_bundle");
- *  }
- * </CODE></PRE>
- * The bundle name is relative to MyException package. This step can omitted if
- * the bundle name is "exceptions".
- * 
- * Note that the implementation correctly resolves error code name collisions
- * across independently developed exception families, as long as resource bundles
- * use unique names. Specifically, error codes follow inheritance and hiding rules
- * similar to Java class static methods. See {@link ExceptionCommon#addExceptionResource}
- * for further details.
- *
- * @author Vlad Roubtsov, (C) 2002
- */
-public
-abstract class AbstractRuntimeException extends RuntimeException implements ICodedException, IThrowableWrapper
-{
-    // public: ................................................................
-
-    /**
-     * Constructs an exception with null message and null cause.
-     */    
-    public AbstractRuntimeException ()
-    {
-        m_cause = null;
-        m_arguments = null;
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and null cause.
-     *
-     * @param message the detail message [can be null]
-     */
-    public AbstractRuntimeException (final String message)
-    {
-        super (message);
-        m_cause = null;
-        m_arguments = null;
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and null cause.
-     *   
-     * @param message the detail message [can be null]
-     * @param arguments message format parameters [can be null or empty]
-     *
-     * @see java.text.MessageFormat
-     */
-    public AbstractRuntimeException (final String message, final Object [] arguments)
-    {
-        super (message);
-        m_cause = null;
-        m_arguments = arguments == null ? null : (Object []) arguments.clone ();
-    }
-    
-    /**
-     * Constructs an exception with null error message/code and given cause.
-     *
-     * @param cause the cause [nested exception] [can be null]
-     */
-    public AbstractRuntimeException (final Throwable cause)
-    {
-        super ();
-        m_cause = cause;
-        m_arguments = null;
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and given cause.
-     *
-     * @param message the detail message [can be null]
-     * @param cause the cause [nested exception] [can be null]
-     */
-    public AbstractRuntimeException (final String message, final Throwable cause)
-    {
-        super (message);
-        m_cause = cause;
-        m_arguments = null;
-    }
-    
-    /**
-     * Constructs an exception with given error message/code and given cause.
-     *
-     * @param message the detail message [can be null]
-     * @param arguments message format parameters [can be null or empty]
-     * @param cause the cause [nested exception] [can be null]
-     *
-     * @see java.text.MessageFormat
-     */
-    public AbstractRuntimeException (final String message, final Object [] arguments, final Throwable cause)
-    {
-        super (message);
-        m_cause = cause;
-        m_arguments = arguments == null ? null : (Object []) arguments.clone ();
-    }
-    
-
-    /**
-     * Overrides base method to support error code lookup and avoid returning nulls.
-     * Note that this does not recurse into any 'cause' for message lookup, it only
-     * uses the data passed into the constructor. Subclasses cannot override.<P>
-     *
-     * Equivalent to {@link #getLocalizedMessage}.
-     *
-     * @return String error message provided at construction time or the result
-     * of toString() if no/null message was provided [never null].
-     */  
-    public final String getMessage ()
-    {
-        if (m_message == null) // not synchronized by design
-        {
-            String msg;
-            final String supermsg = super.getMessage ();
-            final Class _class = getClass ();
-            
-            if (m_arguments == null)
-            {
-                msg = ExceptionCommon.getMessage (_class, supermsg);
-            }
-            else
-            {
-                msg = ExceptionCommon.getMessage (_class, supermsg, m_arguments);
-            }
-            
-            if (msg == null)
-            {
-                // this is the same as what's done in Throwable.toString() [copied here to be independent of future JDK changes]
-                final String className = _class.getName ();
-                
-                msg = (supermsg != null) ? (className + ": " + supermsg) : className;
-            }
-            
-            m_message = msg;
-        }
-        
-        return m_message;
-    }
-    
-    /**
-     * Overrides base method for the sole purpose of making it final.<P>
-     * 
-     * Equivalent to {@link #getMessage}.
-     */
-    public final String getLocalizedMessage ()
-    {
-        // this is the same as what's done in Throwable
-        // [copied here to be independent of future JDK changes]
-        return getMessage ();
-    }
-
-    /**
-     * Overrides Exception.printStackTrace() to (a) force the output to go
-     * to System.out and (b) handle nested exceptions in JDKs prior to 1.4.<P>
-     * 
-     * Subclasses cannot override.
-     */    
-    public final void printStackTrace ()
-    {
-        // NOTE: unlike the JDK implementation, force the output to go to System.out:
-        ExceptionCommon.printStackTrace (this, System.out);
-    }
-    
-    /**
-     * Overrides Exception.printStackTrace() to handle nested exceptions in JDKs prior to 1.4.<P>
-     * 
-     * Subclasses cannot override.
-     */    
-    public final void printStackTrace (final PrintStream s)
-    {
-        ExceptionCommon.printStackTrace (this, s);
-    }
-    
-    /**
-     * Overrides Exception.printStackTrace() to handle nested exceptions in JDKs prior to 1.4.<P>
-     * 
-     * Subclasses cannot override.
-     */ 
-    public final void printStackTrace (final PrintWriter s)
-    {
-        ExceptionCommon.printStackTrace (this, s);
-    }
-
-    // ICodedException:
-    
-    /**
-     * Returns the String that was passed as 'message' constructor argument.
-     * Can be null.
-     *
-     * @return message code string [can be null]
-     */
-    public final String getErrorCode ()
-    {
-        return super.getMessage ();
-    }
-
-    // IThrowableWrapper:
-    
-    /**
-     * This implements {@link IThrowableWrapper}
-     * and also overrides the base method in JDK 1.4+.
-     */
-    public final Throwable getCause ()
-    {
-        return m_cause;
-    }
-
-    public void __printStackTrace (final PrintStream ps)
-    {
-        super.printStackTrace (ps);
-    }
-    
-    public void __printStackTrace (final PrintWriter pw)
-    {
-        super.printStackTrace (pw);
-    }
-
-    /**
-     * Equivalent to {@link ExceptionCommon#addExceptionResource}, repeated here for
-     * convenience. Subclasses should invoke from static initializers <I>only</I>.
-     * 'namespace' should be YourException.class.
-     */
-    public static void addExceptionResource (final Class namespace,
-                                             final String messageResourceBundleName)
-    {
-        // note: 'namespace' will be the most derived class; it is possible to
-        // auto-detect that in a static method but that requires some security
-        // permissions
-        ExceptionCommon.addExceptionResource (namespace, messageResourceBundleName);
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-
-
-    /*
-     * Ensures that this instance can be serialized even if some message parameters
-     * are not serializable objects.
-     */
-    private void writeObject (final ObjectOutputStream out)
-        throws IOException
-    {
-        getMessage (); // transform this instance to serializable form
-        out.defaultWriteObject ();
-    }
-
-    
-    private String m_message; // marshalled/cached result of getMessage()
-    private transient final Object [] m_arguments;
-    // note: this field duplicates functionality available in stock Throwable in JRE 1.4+
-    private final Throwable m_cause;
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/util/exception/ExceptionCommon.java b/core/java12/com/vladium/util/exception/ExceptionCommon.java
deleted file mode 100644
index 5fa98f7..0000000
--- a/core/java12/com/vladium/util/exception/ExceptionCommon.java
+++ /dev/null
@@ -1,503 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ExceptionCommon.java,v 1.1.1.1.2.2 2004/07/10 03:34:52 vlad_r Exp $
- */
-package com.vladium.util.exception;
-
-import java.io.PrintStream;
-import java.io.PrintWriter;
-import java.text.MessageFormat;
-import java.util.Collections;
-import java.util.Enumeration;
-import java.util.HashMap;
-import java.util.Locale;
-import java.util.Map;
-import java.util.ResourceBundle;
-
-import com.vladium.util.IJREVersion;
-
-// TODO: embed build # in error codes
-
-// ----------------------------------------------------------------------------
-/**
- * TODO: javadoc
- * 
- * Based on code <a href="http://www.fawcette.com/javapro/2002_12/online/exception_vroubtsov_12_16_02/default_pf.asp">published</a>
- * by me in JavaPro, 2002.<P>
- * 
- * This non-instantiable class provides static support functions common to
- * {@link AbstractException} and {@link AbstractRuntimeException}.<P>
- *
- * @author Vlad Roubtsov, (C) 2002
- */
-abstract class ExceptionCommon implements IJREVersion
-{
-    // public: ................................................................
-               
-    /**
-     * This method can be called by static initializers of {@link AbstractException}
-     * and {@link AbstractRuntimeException} subclasses in order to add another
-     * resource bundle to the set that is used to look up error codes. This makes
-     * it possible to extend the set of exception error codes across independently
-     * maintained and built projects.<P>
-     *
-     * <BLOCKQUOTE>
-     * Note that this introduces a possibility of error code name clashes. This
-     * is resolved in the following way:
-     * <UL>
-     *     <LI> when <CODE>getMessage(namespace, code)</CODE> is called, 'code'
-     *     is attempted to be looked up in the resource bundle previously keyed
-     *     under 'namespace';
-     *
-     *     <LI> if no such bundle it found or if it does not contain a value for
-     *     key 'code', the same step is repeated for the superclass of 'namespace';
-     *
-     *     <LI> finally, if all of the above steps fail, the root resource bundle
-     *     specified by {@link #ROOT_RESOURCE_BUNDLE_NAME} is searched.
-     * </UL>
-     * 
-     * This strategy ensures that error codes follow inheritance and hiding rules
-     * similar to Java static methods.<P>
-     * </BLOCKQUOTE>
-     *
-     * <B>IMPORTANT:</B> this method must be called from static class initializers
-     * <I>only</I>.<P>
-     *
-     * There is no visible state change if the indicated resource is not found
-     * or if it has been added already under the same key.<P>
-     *
-     * @param namespace the Class object acting as the namespace key for the
-     * resource bundle identified by 'messageResourceBundleName'. <I>This should
-     * be the calling class.</I> [the method is a no-op if this is null]
-     *
-     * @param messageResourceBundleName name of a bundle (path relative to 'namespace'
-     * package) to add to the set from which error code mappings are retrieved
-     * [the method is a no-op if this is null or an empty string]
-     * 
-     * @return ResourceBundle that corresponds to 'namespace' key or null if
-     * no such bundle could be loaded
-     *
-     * @throws Error if 'namespace' does not correspond to an exception class derived
-     * from {@link AbstractException} or {@link AbstractRuntimeException}.
-     *
-     * @see #lookup
-     */
-    public static ResourceBundle addExceptionResource (final Class namespace,
-                                                       final String messageResourceBundleName)
-    {
-        if ((namespace != null) && (messageResourceBundleName != null)
-            && (messageResourceBundleName.length () > 0))
-        {
-            // bail out if the some other exception hierarchy attempts
-            // to use this functionality:
-            if (! ABSTRACT_EXCEPTION.isAssignableFrom (namespace)
-                && ! ABSTACT_RUNTIME_EXCEPTION.isAssignableFrom (namespace))
-            {
-                throw new Error ("addExceptionResource(): class [" + namespace +
-                    "] is not a subclass of " + ABSTRACT_EXCEPTION.getName () +
-                    " or " + ABSTACT_RUNTIME_EXCEPTION.getName ());
-            }
-            
-            // try to load resource bundle
-            
-            ResourceBundle temprb = null;
-            String nameInNamespace = null;
-            try
-            {
-                nameInNamespace = getNameInNamespace (namespace, messageResourceBundleName);
-                
-                //temprb = ResourceBundle.getBundle (nameInNamespace);
-                
-                ClassLoader loader = namespace.getClassLoader ();
-                if (loader == null) loader = ClassLoader.getSystemClassLoader ();
-                
-                temprb = ResourceBundle.getBundle (nameInNamespace, Locale.getDefault (), loader);
-            }
-            catch (Throwable ignore)
-            {
-               // ignored intentionally: if the exception codes rb is absent,
-               // we are still in a supported configuration
-               temprb = null;
-            }
-            
-            if (temprb != null)
-            {
-                synchronized (s_exceptionCodeMap)
-                {
-                    final ResourceBundle currentrb =
-                        (ResourceBundle) s_exceptionCodeMap.get (namespace); 
-                    if (currentrb != null)
-                        return currentrb;
-                    else
-                    {
-                        s_exceptionCodeMap.put (namespace, temprb);
-                        return temprb;
-                    }
-                }
-            }
-        }
-        
-        return null;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................  
-
-
-    static void printStackTrace (Throwable t, final PrintWriter out)
-    {
-        if (JRE_1_4_PLUS)
-        {
-            if (t instanceof IThrowableWrapper)
-            {
-                final IThrowableWrapper tw = (IThrowableWrapper) t;
-                
-                tw.__printStackTrace (out); 
-            }
-            else
-            {
-                t.printStackTrace (out);
-            }
-        }
-        else
-        {
-            for (boolean first = true; t != null; )
-            {
-                if (first)
-                    first = false;
-                else
-                {
-                    out.println ();
-                    out.println (NESTED_THROWABLE_HEADER);                
-                }
-                
-                if (t instanceof IThrowableWrapper)
-                {
-                    final IThrowableWrapper tw = (IThrowableWrapper) t;
-                    
-                    tw.__printStackTrace (out);
-                    t = tw.getCause (); 
-                }
-                else
-                {
-                    t.printStackTrace (out);
-                    break;
-                }
-            }
-        }
-    }
-    
-    
-    static void printStackTrace (Throwable t, final PrintStream out)
-    {
-        if (JRE_1_4_PLUS)
-        {
-            if (t instanceof IThrowableWrapper)
-            {
-                final IThrowableWrapper tw = (IThrowableWrapper) t;
-                
-                tw.__printStackTrace (out); 
-            }
-            else
-            {
-                t.printStackTrace (out);
-            }
-        }
-        else
-        {
-            for (boolean first = true; t != null; )
-            {
-                if (first)
-                    first = false;
-                else
-                {
-                    out.println ();
-                    out.println (NESTED_THROWABLE_HEADER);                
-                }
-                
-                if (t instanceof IThrowableWrapper)
-                {
-                    final IThrowableWrapper tw = (IThrowableWrapper) t;
-                    
-                    tw.__printStackTrace (out);
-                    t = tw.getCause (); 
-                }
-                else
-                {
-                    t.printStackTrace (out);
-                    break;
-                }
-            }
-        }
-    }
-    
-
-    /**
-     * Provides support for lookup of exception error codes from {@link AbstractException}
-     * and {@link AbstractRuntimeException} and their subclasses.
-     *
-     * @param namespace the Class object acting as the key to the namespace from
-     * which to retrieve the description for 'code' [can be null, in which case
-     * only the root namespace is used for lookup]
-     *
-     * @param code the message string value that was passed into exception
-     * constructor [can be null, in which case null is returned].
-     *
-     * @return looked-up error message or the error code if it could not be
-     * looked up [null is returned on null 'code' input only].
-     *
-     * This method does not throw.
-     *
-     * @see AbstractException#getMessage
-     * @see AbstractRuntimeException#getMessage
-     */
-    static String getMessage (final Class namespace, final String code)
-    {
-        if (code == null) return null;
-        
-        try
-        {                      
-            if (code.length () > 0)
-            {
-                // look the code up in the resource bundle:
-                final String msg = lookup (namespace, code);     
-                if (msg == null)
-                {
-                    // if code lookup failed, return 'code' as is:
-                    return code;
-                }
-                else
-                {
-                    return EMBED_ERROR_CODE ? "[" + code + "] " + msg : msg;
-                }
-           }
-           else
-           {
-               return "";
-           }
-        }
-        catch (Throwable t)
-        {
-            // this method must never fail: default to returning the input
-            // verbatim on all unexpected problems
-            return code;
-        }
-    }
-    
-    /**
-     * Provides support for lookup of exception error codes from {@link AbstractException}
-     * and {@link AbstractRuntimeException} and their subclasses.
-     *
-     * @param namespace the Class object acting as the key to the namespace from
-     * which to retrieve the description for 'code' [can be null, in which case
-     * only the root namespace is used for lookup]
-     *
-     * @param code the message string value that was passed into exception
-     * constructor [can be null, in which case null is returned].
-     *
-     * @param arguments java.text.MessageFormat-style parameters to be substituted
-     * into the error message once it is looked up. 
-     *
-     * @return looked-up error message or the error code if it could not be
-     * looked up [null is returned on null 'code' input only].
-     *
-     * This method does not throw.
-     *
-     * @see AbstractException#getMessage
-     * @see AbstractRuntimeException#getMessage
-     */
-    static String getMessage (final Class namespace, final String code, final Object [] arguments)
-    {
-        if (code == null) return null;
-        final String pattern = getMessage (namespace, code);
-
-        // assertion: pattern != null
-        
-        if ((arguments == null) || (arguments.length == 0))
-        {
-            return pattern;
-        }
-        else
-        {
-            try
-            {
-                return MessageFormat.format (pattern, arguments);
-            }
-            catch (Throwable t)
-            {
-                // this method cannot fail: default to returning the input
-                // verbatim on all unexpected problems:
-                
-                final StringBuffer msg = new StringBuffer (code + EOL);
-                
-                for (int a = 0; a < arguments.length; a ++)
-                {
-                    msg.append ("\t{" + a + "} = [");
-                    final Object arg = arguments [a];
-                    try
-                    {
-                        msg.append (arg.toString ());
-                    }
-                    catch (Throwable e) // guard against bad toString() overrides
-                    {
-                        if (arg != null)
-                            msg.append (arg.getClass ().getName ());
-                        else
-                            msg.append ("null");
-                    }
-                    msg.append ("]");
-                    msg.append (EOL);
-                }
-                
-                return msg.toString ();
-            }
-        }
-    }
-    
-    // private: ...............................................................
-
-
-    private ExceptionCommon () {} // prevent subclassing
-        
-    /**
-     * Internal property lookup method. It implements the lookup scheme described
-     * in {@link #addExceptionResource}.
-     * 
-     * @return property value corresponding to 'propertyName' [null if lookup fails]
-     */
-    private static String lookup (Class namespace, final String propertyName)
-    {
-        if (propertyName == null) return null;
-        
-        // note: the following does not guard against exceptions that do not subclass
-        // our base classes [done elsewhere], however it will not crash either
-        
-        // check extension bundles:
-        if (namespace != null)
-        {
-            ResourceBundle rb;
-            while (namespace != ABSTRACT_EXCEPTION && namespace != ABSTACT_RUNTIME_EXCEPTION
-                   && namespace != THROWABLE && namespace != null)
-            {
-                synchronized (s_exceptionCodeMap)
-                {
-                    rb = (ResourceBundle) s_exceptionCodeMap.get (namespace);
-                    if (rb == null)
-                    {
-                        // check if there is a default bundle to be loaded for this namespace: 
-                        if ((rb = addExceptionResource (namespace, "exceptions")) == null)
-                        {
-                            // add an immutable empty bundle to avoid this check in the future:
-                            s_exceptionCodeMap.put (namespace, EMPTY_RESOURCE_BUNDLE);
-                        }
-                    }
-                }
-                
-                if (rb != null)
-                {
-                    String propertyValue = null;
-                    try
-                    {
-                        propertyValue = rb.getString (propertyName);
-                    }
-                    catch (Throwable ignore) {}
-                    if (propertyValue != null) return propertyValue;
-                }
-                
-                // walk the inheritance chain for 'namespace':
-                namespace = namespace.getSuperclass ();
-            }
-        }
-        
-        // if everything fails, check the root bundle:
-        if (ROOT_RESOURCE_BUNDLE != null)
-        {
-            String propertyValue = null;
-            try
-            {
-                propertyValue = ROOT_RESOURCE_BUNDLE.getString (propertyName);
-            }
-            catch (Throwable ignore) {}
-            if (propertyValue != null) return propertyValue;
-        }
-        
-        return null;
-    }
-    
-    private static String getNameInNamespace (final Class namespace, final String name)
-    {
-        if (namespace == null) return name;
-        
-        final String namespaceName = namespace.getName ();
-        final int lastDot = namespaceName.lastIndexOf ('.');
-        
-        if (lastDot <= 0)
-            return name;
-        else
-            return namespaceName.substring (0, lastDot + 1)  + name;
-    }
-    
-
-    // changes this to 'false' to eliminate repetition of error codes in
-    // the output of getMessage(): 
-    private static final boolean EMBED_ERROR_CODE = true;
-
-    // the name of the 'root' message resource bundle, derived as
-    // [this package name + ".exceptions"]:
-    private static final String ROOT_RESOURCE_BUNDLE_NAME;      // set in <clinit>
-    
-    // the root resource bundle; always checked if all other lookups fail:    
-    private static final ResourceBundle ROOT_RESOURCE_BUNDLE;   // set in <clinit>
-    
-    // static cache of all loaded resource bundles, populated via addExceptionResource():
-    private static final Map /* Class -> ResourceBundle */ s_exceptionCodeMap = new HashMap ();
-    
-    // misc constants:
-    
-    private static final String NESTED_THROWABLE_HEADER = "[NESTED EXCEPTION]:";
-    private static final Class THROWABLE                    = Throwable.class;
-    private static final Class ABSTRACT_EXCEPTION           = AbstractException.class;
-    private static final Class ABSTACT_RUNTIME_EXCEPTION    = AbstractRuntimeException.class;
-    /*private*/ static final Enumeration EMPTY_ENUMERATION  = Collections.enumeration (Collections.EMPTY_SET);    
-    private static final ResourceBundle EMPTY_RESOURCE_BUNDLE = new ResourceBundle ()
-    {
-        public Object handleGetObject (final String key)
-        {
-            return null;
-        }
-        
-        public Enumeration getKeys ()
-        {
-            return EMPTY_ENUMERATION;
-        }
-    };
-    
-    // end-of-line terminator for the current platform:
-    private static final String EOL = System.getProperty ("line.separator", "\n");
-    
-    
-    static
-    {
-        // set the name of ROOT_RESOURCE_BUNDLE_NAME:
-        ROOT_RESOURCE_BUNDLE_NAME = getNameInNamespace (ExceptionCommon.class, "exceptions");
-                
-        // set the root resource bundle:
-        ResourceBundle temprb = null;
-        try
-        {
-            temprb = ResourceBundle.getBundle (ROOT_RESOURCE_BUNDLE_NAME);
-        }
-        catch (Throwable ignore)
-        {
-            // if the exception codes rb is absent, we are still in a supported configuration
-        }
-        ROOT_RESOURCE_BUNDLE = temprb;        
-    }
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/util/exception/Exceptions.java b/core/java12/com/vladium/util/exception/Exceptions.java
deleted file mode 100644
index 1ee691a..0000000
--- a/core/java12/com/vladium/util/exception/Exceptions.java
+++ /dev/null
@@ -1,47 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: Exceptions.java,v 1.1.1.1 2004/05/09 16:57:58 vlad_r Exp $
- */
-package com.vladium.util.exception;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2002
- */
-public
-abstract class Exceptions
-{
-    // public: ................................................................
-    
-    public static boolean unexpectedFailure (final Throwable t, final Class [] expected)
-    {
-        if (t == null) return false;
-        if (expected == null) return true;
-        
-        final Class reClass = t.getClass ();
-        
-        for (int e = 0; e < expected.length; ++ e)
-        {
-            if (expected [e] == null) continue;
-            if (expected [e].isAssignableFrom (reClass))
-                return false;
-        }
-        
-        return true;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private Exceptions () {} // this class is not extendible
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/com/vladium/util/exception/ICodedException.java b/core/java12/com/vladium/util/exception/ICodedException.java
deleted file mode 100644
index 0121226..0000000
--- a/core/java12/com/vladium/util/exception/ICodedException.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ICodedException.java,v 1.1.1.1 2004/05/09 16:57:58 vlad_r Exp $
- */
-package com.vladium.util.exception;
- 
-// ----------------------------------------------------------------------------
-/**
- * TODO: javadoc
- * 
- * This interface is implemented by {@link AbstractException} and
- * {@link AbstractRuntimeException} to provide a common interface
- * for accessing error codes.<P>
- * 
- * An error code is a compact string representing the nature of exception
- * in a programmatic locale-independent way. It can be used as a key that maps
- * to a human-readable error message in a resource bundle. For details, see
- * the exception classes mentioned above.
- * 
- * @author Vlad Roubtsov, (C) 2002
- */
-public
-interface ICodedException
-{
-    // public: ................................................................
-    
-    /**
-     * Returns the String that was passed as 'message' argument to an exception
-     * constructor. For a coded exception this will be the compact error code
-     * [and different from the result of <code>getMessage()</code>], otherwise
-     * this will be traditional error message.
-     *
-     * @return message code string [can be null]
-     */
-    String getErrorCode ();
-
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/com/vladium/util/exception/IThrowableWrapper.java b/core/java12/com/vladium/util/exception/IThrowableWrapper.java
deleted file mode 100644
index 66174c0..0000000
--- a/core/java12/com/vladium/util/exception/IThrowableWrapper.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IThrowableWrapper.java,v 1.1.1.1 2004/05/09 16:57:58 vlad_r Exp $
- */
-package com.vladium.util.exception;
-
-import java.io.PrintStream;
-import java.io.PrintWriter;
-
-// ----------------------------------------------------------------------------
-/**
- * TODO: javadoc
- * 
- * Any exception that wraps around another exception and wishes to be fully 
- * inspectable by {@link ExceptionCommon} should implement this interface.
- * Note that JDK 1.4+ obsoletes the need for an explicit interface like this,
- * although the implementation in {@link ExceptionCommon} is upwards compatible
- * with it.
- * 
- * @author Vlad Roubtsov, (C) 2002
- */
-interface IThrowableWrapper
-{
-    // public: ................................................................
-
-    /**
-     * Gets the Throwable being wrapped. This method signature is the same as
-     * Throwable.getCause() in J2SE 1.4.
-     * 
-     * @return Throwable being wrapped by this object [can be null].
-     */
-    Throwable getCause ();
-     
-    /**
-     * Every exception hierarchy implementing this interface must ensure that
-     * this method delegates to super.printStackTrace(pw) where 'super' is the
-     * first superclass not implementing IThrowableWrapper. This is used by
-     * {@link ExceptionCommon} to avoid infinite
-     * recursion and is not meant to be called by other classes.
-     */
-    void __printStackTrace (PrintWriter pw);
-
-    /**
-     * Every exception hierarchy implementing this interface must ensure that
-     * this method delegates to super.printStackTrace(ps) where 'super' is the
-     * first superclass not implementing IThrowableWrapper. This is used by
-     * {@link ExceptionCommon} to avoid infinite
-     * recursion and is not meant to be called by other classes.
-     */
-    void __printStackTrace (PrintStream ps);
-
-} // end of interface
-// ----------------------------------------------------------------------------
diff --git a/core/java12/emma.java b/core/java12/emma.java
deleted file mode 100644
index dc64cf5..0000000
--- a/core/java12/emma.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: emma.java,v 1.1.1.1.2.1 2004/07/16 23:32:29 vlad_r Exp $
- */
-import com.vladium.emma.IAppConstants;
-import com.vladium.emma.Command;
-import com.vladium.emma.EMMARuntimeException;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class emma
-{
-    // public: ................................................................
-    
-    // TODO: set m_out consistently with LoggerInit    
-    
-    public static void main (final String [] args)
-        throws EMMARuntimeException
-    {
-        // TODO: proper usage, arg validation, etc
-        
-        if ((args.length == 0) || args [0].startsWith ("-h"))
-        {
-            System.out.println (USAGE);
-            return;
-        }
-        
-        final String commandName = args [0];
-        final String [] commandArgs = new String [args.length - 1];
-        System.arraycopy (args, 1, commandArgs, 0, commandArgs.length);
-        
-        final Command command = Command.create (commandName, "emma ".concat (commandName), commandArgs);
-        command.run ();
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-    
-    
-    private static final String EOL = System.getProperty ("line.separator", "\n"); 
-    
-    private static final String USAGE =
-    "emma usage: emma <command> [command options]," + EOL +
-    "  where <command> is one of:" + EOL +
-    EOL +
-    "   run     application runner {same as 'emmarun' tool};" + EOL +
-    "   instr   offline instrumentation processor;" + EOL +
-    "   report  offline report generator;" + EOL +
-    "   merge   offline data file merge processor." + EOL +
-    EOL +
-    "  {use '<command> -h' to see usage help for a given command}" + EOL +
-    EOL +
-    IAppConstants.APP_USAGE_BUILD_ID;
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java12/emmarun.java b/core/java12/emmarun.java
deleted file mode 100644
index cc5f76d..0000000
--- a/core/java12/emmarun.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: emmarun.java,v 1.1.1.1.2.1 2004/07/16 23:32:29 vlad_r Exp $
- */
-import com.vladium.emma.Command;
-import com.vladium.emma.EMMARuntimeException;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-final class emmarun
-{
-    // public: ................................................................
-    
-    // TODO: set m_out consistently with LoggerInit    
-    
-    public static void main (final String [] args)
-        throws EMMARuntimeException
-    {
-        final Command command = Command.create ("run", emmarun.class.getName (), args);
-        command.run ();
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/core/java13/com/vladium/util/exit/ExitHookManager.java b/core/java13/com/vladium/util/exit/ExitHookManager.java
deleted file mode 100644
index 2bcee9f..0000000
--- a/core/java13/com/vladium/util/exit/ExitHookManager.java
+++ /dev/null
@@ -1,123 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ExitHookManager.java,v 1.1.1.1 2004/05/09 16:57:58 vlad_r Exp $
- */
-package com.vladium.util.exit;
-
-import java.util.HashMap;
-import java.util.Map;
-
-import com.vladium.util.IJREVersion;
-import com.vladium.util.Property;
-import com.vladium.emma.IAppConstants;
-
-// ----------------------------------------------------------------------------
-/**
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-abstract class ExitHookManager implements IJREVersion
-{
-    // public: ................................................................
-    
-    // TOTO: handle thread groups as well?
-    
-    public abstract boolean addExitHook (Runnable runnable);
-    public abstract boolean removeExitHook (Runnable runnable);
-    
-    public static synchronized ExitHookManager getSingleton ()
-    {
-        if (s_singleton == null)
-        {
-            if (JRE_1_3_PLUS)
-            {
-                s_singleton = new JRE13ExitHookManager ();
-            }
-            else
-            {
-                throw new UnsupportedOperationException ("no shutdown hook manager available [JVM: " + Property.getSystemFingerprint () + "]");
-            }
-        }
-        
-        return s_singleton;
-    }
-    
-    // protected: .............................................................
-    
-    
-    protected ExitHookManager () {}
-
-    // package: ...............................................................
-
-    // private: ...............................................................
-    
-    
-    private static final class JRE13ExitHookManager extends ExitHookManager
-    {
-        public synchronized boolean addExitHook (final Runnable runnable)
-        {
-            if ((runnable != null) && ! m_exitThreadMap.containsKey (runnable))
-            {
-                final Thread exitThread = new Thread (runnable, IAppConstants.APP_NAME + " shutdown handler thread");
-                
-                try
-                {
-                    Runtime.getRuntime ().addShutdownHook (exitThread);
-                    m_exitThreadMap.put (runnable, exitThread); // TODO: use identity here
-                    
-                    return true;
-                }
-                catch (Exception e)
-                {
-                    System.out.println ("exception caught while adding a shutdown hook:");
-                    e.printStackTrace (System.out);
-                }
-            }
-            
-            return false;
-        }
-        
-        public synchronized boolean removeExitHook (final Runnable runnable)
-        {
-            if (runnable != null)
-            {
-                final Thread exitThread = (Thread) m_exitThreadMap.get (runnable);  // TODO: use identity here
-                
-                if (exitThread != null)
-                {
-                    try
-                    {
-                        Runtime.getRuntime ().removeShutdownHook (exitThread);
-                        m_exitThreadMap.remove (runnable);
-                        
-                        return true;
-                    }
-                    catch (Exception e)
-                    {
-                        System.out.println ("exception caught while removing a shutdown hook:");
-                        e.printStackTrace (System.out);
-                    }
-                }
-            }
-            
-            return false;
-        }
-        
-        JRE13ExitHookManager ()
-        {
-            m_exitThreadMap = new HashMap ();
-        }
-        
-        
-        private final Map /* Runnable->Thread */ m_exitThreadMap;
-        
-    } // end of nested class
-    
-    private static ExitHookManager s_singleton;
-    
-} // end of class
-// ----------------------------------------------------------------------------
diff --git a/core/java14/com/vladium/util/IJREVersion.java b/core/java14/com/vladium/util/IJREVersion.java
deleted file mode 100644
index 7f3331a..0000000
--- a/core/java14/com/vladium/util/IJREVersion.java
+++ /dev/null
@@ -1,93 +0,0 @@
-/* Copyright (C) 2003 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: IJREVersion.java,v 1.1.1.1.2.1 2004/07/10 03:34:52 vlad_r Exp $
- */
-package com.vladium.util;
-
-// ----------------------------------------------------------------------------
-/**
- * A constant collection to detect the current JRE version. Note that this code
- * is more sophisticated then a mere check of "java.version" or "java.class.version"
- * and similar system properties because some JVMs allow overriding those
- * by the user (e.g., from the command line). This implementation relies on
- * the core classes only and tries to minimize the number of security-sensitive
- * methods it uses.<P>
- * 
- * This interface is supported in Java 1.1+ and should be compiled with class
- * version stamp 45.3 (-target 1.1).
- * 
- * @author Vlad Roubtsov, (C) 2003
- */
-public
-interface IJREVersion
-{
-    // public: ................................................................
-
-    /** 'true' iff the current runtime version is 1.2 or later */
-    boolean JRE_1_2_PLUS = _JREVersion._JRE_1_2_PLUS; // static final but not inlinable
-    /** 'true' iff the current runtime version is 1.3 or later */
-    boolean JRE_1_3_PLUS = _JREVersion._JRE_1_3_PLUS; // static final but not inlinable
-    /** 'true' iff the current runtime version is 1.4 or later */
-    boolean JRE_1_4_PLUS = _JREVersion._JRE_1_4_PLUS; // static final but not inlinable
-    
-    // supporting Java 1.5 is trivial...
-    
-    boolean JRE_SUN_SIGNAL_COMPATIBLE = _JREVersion._JRE_SUN_SIGNAL_COMPATIBLE;
-    
-    /*
-     * Use a dummy nested class to fake a static initializer for the outer
-     * interface (I want IJREVersion as an interface and not a class so that
-     * all JRE_XXX constants could be imported via "implements").
-     */
-    abstract class _JREVersion
-    {
-        static final boolean _JRE_1_2_PLUS; // set in <clinit>
-        static final boolean _JRE_1_3_PLUS; // set in <clinit>    
-        static final boolean _JRE_1_4_PLUS; // set in <clinit>
-        
-        static final boolean _JRE_SUN_SIGNAL_COMPATIBLE; // set in <clinit>
-        
-        private _JREVersion () {} // prevent subclassing
-    
-        static
-        {
-            _JRE_1_2_PLUS = ((SecurityManager.class.getModifiers () & 0x0400) == 0);
-
-            boolean temp = false;            
-            if (_JRE_1_2_PLUS)
-            {
-                try
-                {
-                    StrictMath.abs (1.0);
-                    temp = true;
-                }
-                catch (Error ignore) {}
-            }
-            _JRE_1_3_PLUS = temp;
-            
-            if (temp)
-            {
-                temp = false;
-                try
-                {
-                    " ".subSequence (0, 0);
-                    temp = true;
-                }
-                catch (NoSuchMethodError ignore) {}
-            }
-            _JRE_1_4_PLUS = temp;
-            
-            temp = false;
-            
-            _JRE_SUN_SIGNAL_COMPATIBLE = temp;
-        }
-
-    } // end of nested class
-
-} // end of interface
-// ----------------------------------------------------------------------------
-
diff --git a/core/res/com/vladium/emma/data/merge_usage.res b/core/res/com/vladium/emma/data/merge_usage.res
deleted file mode 100644
index 2ebf4d6..0000000
--- a/core/res/com/vladium/emma/data/merge_usage.res
+++ /dev/null
@@ -1,52 +0,0 @@
-
-'in', 'input':
-	required, mergeable, values: 1,
-	'<list of files>',
-	"list of meta/coverage data files";
-
-'out', 'outfile':
-	optional, values: 1,
-	'<file>',
-	"merged data output file (defaults to 'coverage.es')";
-
-'p', 'props', 'properties':
-	optional, values: 1,
-	'<properties file>',
-	"properties override file";
-
-'D':
-	optional, mergeable, detailedonly, pattern, values: 1,
-	'<value>',
-	"generic property override";
-
-'exit':
-	optional, detailedonly, values: 0,
-	"use System.exit() on termination";
-
-'verbose':
-	optional, detailedonly, values: 0,
-	excludes {'silent', 'quiet', 'debug'},
-	"verbose output operation";
-
-'quiet':
-	optional, detailedonly, values: 0,
-	excludes {'silent', 'verbose', 'debug'},
-	"quiet operation (ignore all but warnings and severe errors)";
-
-'silent':
-	optional, detailedonly, values: 0,
-	excludes {'quiet', 'verbose', 'debug'},
-	"extra-quiet operation (ignore all but severe errors)";
-
-'debug', 'loglevel': 
-	optional, detailedonly, values: ?,
-	'[<debug trace level>]',
-	excludes {'verbose', 'quiet', 'silent'},
-	"debug tracing level";
-
-'debugcls':
-	optional, detailedonly, values: 1,
-	'<debug trace class mask>',
-	"class mask for debug tracing";
-
-
diff --git a/core/res/com/vladium/emma/exceptions.properties b/core/res/com/vladium/emma/exceptions.properties
deleted file mode 100644
index 217ad78..0000000
--- a/core/res/com/vladium/emma/exceptions.properties
+++ /dev/null
@@ -1,63 +0,0 @@
-# -----------------------------------------------------------------------------
-# this is loaded as a resource bundle by com.vladium.emma.* exceptions
-# -----------------------------------------------------------------------------
-
-UNEXPECTED_FAILURE: \
-unexpected failure {0}, please submit a bug report to: ''{1}''
-
-INVALID_PARAMETER_VALUE: \
-value ''{1}'' is not valid for parameter ''{0}''
-
-REQUIRED_PARAMETER_MISSING: \
-required parameter [{0}] is not specified 
-
-INVALID_COLUMN_NAME: \
-invalid report column name [{0}]
-
-SECURITY_RESTRICTION: \
-current security settings are too restrictive for {0} to operate
-
-MAIN_CLASS_BAD_DELEGATION: \
-the application class [{1}] that you are trying to launch was not loaded \
-by {0} instrumenting classloader, possibly because is was not listed in \
-the '-cp' option: {0} will not be able to collect any coverage data. The \
-actual classloader was: {2}
-
-MAIN_CLASS_NOT_FOUND: \
-application class [{0}] could not be loaded
-
-MAIN_CLASS_LOAD_FAILURE: \
-application class [{0}] could not be loaded and initialized, most likely due \
-to static initializer failure: {1}
-
-MAIN_METHOD_NOT_FOUND: \
-application class [{0}] does not have a runnable public main() method
-
-MAIN_METHOD_FAILURE: \
-{0}.main() method failure: {1}
-
-REPORT_GEN_FAILURE: \
-failed to generate report
-
-REPORT_IO_FAILURE: \
-exception occurred while writing report file(s):
-
-CLASS_STAMP_MISMATCH: \
-runtime version of class [{0}] in the coverage data is not consistent \
-with the version of this class in the metadata, possibly because stale \
-metadata is being used for report generation.
-
-OUT_MKDIR_FAILURE: \
-output directory [{0}] could not be created
-
-INSTR_IO_FAILURE: \
-exception occurred while writing instrumented file(s):
-
-OUT_IO_FAILURE: \
-exception occurred while writing output file [{0}]:
-
-ARGS_IO_FAILURE: \
-exception while processing settings:
-
-# -----------------------------------------------------------------------------
-# end of file
diff --git a/core/res/com/vladium/emma/instr/instr_usage.res b/core/res/com/vladium/emma/instr/instr_usage.res
deleted file mode 100644
index 56a6699..0000000
--- a/core/res/com/vladium/emma/instr/instr_usage.res
+++ /dev/null
@@ -1,72 +0,0 @@
-
-'ip', 'cp', 'instrpath':
-	required, mergeable, values: 1,
-	'<class directories and zip/jar files>',
-	"instrumentation path";
-
-'d', 'dir', 'outdir':
-	optional, values: 1,
-	'<directory>',
-	"instrumentation output directory (required for non-overwrite output modes)";
-
-'out', 'outfile':
-	optional, values: 1,
-	'<file>',
-	"metadata output file (defaults to 'coverage.em')";
-
-'merge':
-	optional, values: 1,
-    '(y[es]|n[o])',
-	"merge metadata into output file, if it exists";
-
-'m', 'outmode':
-	optional, values: 1,
-	'(copy|overwrite|fullcopy)',
-	"output mode (defaults to 'copy')";
-
-'ix', 'filter':
-	optional, mergeable, values: 1,
-	'<class name wildcard patterns>',
-	"coverage inclusion/exclusion patterns {?,*}";
-
-'p', 'props', 'properties':
-	optional, values: 1,
-	'<properties file>',
-	"properties override file";
-
-'D':
-	optional, mergeable, detailedonly, pattern, values: 1,
-	'<value>',
-	"generic property override";
-
-'exit':
-	optional, detailedonly, values: 0,
-	"use System.exit() on termination";
-
-'verbose':
-	optional, detailedonly, values: 0,
-	excludes {'silent', 'quiet', 'debug'},
-	"verbose output operation";
-
-'quiet':
-	optional, detailedonly, values: 0,
-	excludes {'silent', 'verbose', 'debug'},
-	"quiet operation (ignore all but warnings and severe errors)";
-
-'silent':
-	optional, detailedonly, values: 0,
-	excludes {'quiet', 'verbose', 'debug'},
-	"extra-quiet operation (ignore all but severe errors)";
-
-'debug', 'loglevel': 
-	optional, detailedonly, values: ?,
-	'[<debug trace level>]',
-	excludes {'verbose', 'quiet', 'silent'},
-	"debug tracing level";
-
-'debugcls':
-	optional, detailedonly, values: 1,
-	'<debug trace class mask>',
-	"class mask for debug tracing";
-
-
diff --git a/core/res/com/vladium/emma/report/report_usage.res b/core/res/com/vladium/emma/report/report_usage.res
deleted file mode 100644
index f91c241..0000000
--- a/core/res/com/vladium/emma/report/report_usage.res
+++ /dev/null
@@ -1,57 +0,0 @@
-
-'in', 'input':
-	required, mergeable, values: 1,
-	'<list of files>',
-	"list of meta/coverage data files";
-
-'r', 'report':
-	required, mergeable, values: 1,
-	'<list of {txt|html|xml}>',
-	"coverage report type list";
-
-'sp', 'sourcepath':
-	optional, mergeable, values: 1,
-	'<list of source directories>',
-	"Java source path for generating reports";
-
-'p', 'props', 'properties':
-	optional, values: 1,
-	'<properties file>',
-	"properties override file";
-
-'D':
-	optional, mergeable, detailedonly, pattern, values: 1,
-	'<value>',
-	"generic property override";
-
-'exit':
-	optional, detailedonly, values: 0,
-	"use System.exit() on termination";
-
-'verbose':
-	optional, detailedonly, values: 0,
-	excludes {'silent', 'quiet', 'debug'},
-	"verbose output operation";
-
-'quiet':
-	optional, detailedonly, values: 0,
-	excludes {'silent', 'verbose', 'debug'},
-	"quiet operation (ignore all but warnings and severe errors)";
-
-'silent':
-	optional, detailedonly, values: 0,
-	excludes {'quiet', 'verbose', 'debug'},
-	"extra-quiet operation (ignore all but severe errors)";
-
-'debug', 'loglevel': 
-	optional, detailedonly, values: ?,
-	'[<debug trace level>]',
-	excludes {'verbose', 'quiet', 'silent'},
-	"debug tracing level";
-
-'debugcls':
-	optional, detailedonly, values: 1,
-	'<debug trace class mask>',
-	"class mask for debug tracing";
-
-
diff --git a/core/res/com/vladium/emma/rt/RTExitHook.closure b/core/res/com/vladium/emma/rt/RTExitHook.closure
deleted file mode 100644
index 366a00a..0000000
--- a/core/res/com/vladium/emma/rt/RTExitHook.closure
+++ /dev/null
@@ -1,3 +0,0 @@
-#this file is auto-generated, do not edit
-#Fri Feb 08 12:18:59 PST 2008
-closure=com.vladium.util.ResourceLoader,com.vladium.emma.rt.RTCoverageDataPersister,com.vladium.util.IntSet,com.vladium.logging.Logger,com.vladium.util.IntSet$Entry,com.vladium.emma.data.DataFactory$UCFileOutputStream,com.vladium.emma.rt.RTExitHook,com.vladium.util.ClassLoaderResolver$CallerResolver,com.vladium.emma.data.CoverageData,com.vladium.util.ClassLoadContext,com.vladium.emma.data.ClassDescriptor,com.vladium.util.Property$SystemPropertyLookup,com.vladium.util.IConstants,com.vladium.emma.data.IMetaData,com.vladium.emma.data.CoverageOptions,com.vladium.util.ClassLoaderResolver,com.vladium.emma.data.ICoverageData$DataHolder,com.vladium.emma.data.ISessionData,com.vladium.emma.data.DataFactory$UCFileInputStream,com.vladium.emma.data.IMetadataConstants,com.vladium.emma.data.MethodDescriptor,com.vladium.util.Property$SystemRedirectsLookup,com.vladium.emma.data.MetaData,com.vladium.logging.Logger$1,com.vladium.util.IClassLoadStrategy,com.vladium.emma.data.DataFactory$RandomAccessFileInputStream,com.vladium.emma.data.IMergeable,com.vladium.util.IntObjectMap,com.vladium.util.Property,com.vladium.logging.Logger$ThreadLocalStack,com.vladium.emma.data.DataFactory,com.vladium.emma.data.ICoverageData,com.vladium.emma.data.DataFactory$RandomAccessFileOutputStream,com.vladium.util.IntObjectMap$Entry,com.vladium.util.XProperties,com.vladium.util.ClassLoaderResolver$DefaultClassLoadStrategy,com.vladium.logging.ILogLevels,com.vladium.util.ClassLoaderResolver$1,com.vladium.util.Property$FilePropertyLookup
diff --git a/core/res/com/vladium/emma/run_usage.res b/core/res/com/vladium/emma/run_usage.res
deleted file mode 100644
index 42d6f7c..0000000
--- a/core/res/com/vladium/emma/run_usage.res
+++ /dev/null
@@ -1,88 +0,0 @@
-
-'cp', 'classpath':
-	optional, mergeable, values: 1,
-	'<list of directories and zip/jar files>',
-    excludes { 'jar' },
-	"load/coverage classpath";
-
-'jar':
-	optional, values: 0,
-    excludes { 'cp' },
-	"run an executable jar file";
-
-'f', 'fullmetadata':
-	optional, values: 0,
-	"consider the entire classpath for coverage {including classes that are never loaded}";
-
-'ix', 'filter':
-	optional, mergeable, values: 1,
-	'<class name wildcard patterns>',
-	"coverage inclusion/exclusion patterns {?,*}";
-
-'r', 'report':
-	optional, mergeable, values: 1,
-	'<list of {txt|html|xml}>',
-	"coverage report type list";
-
-'sp', 'sourcepath':
-	optional, mergeable, values: 1,
-	'<list of source directories>',
-	"Java source path for generating reports";
-
-'raw', 'sessiondata':
-	optional, values: 0,
-	"dump raw session data file";
-
-'out', 'outfile':
-	optional, values: 1,
-	'<file>',
-    requires { 'raw' },
-	"raw session data output file (defaults to 'coverage.es')";
-
-'merge':
-	optional, values: 1,
-    '<y[es]|n[o]>',
-    requires { 'raw' },
-	"merge session data into output file, if it exists";
-
-'p', 'props', 'properties':
-	optional, values: 1,
-	'<properties file>',
-	"properties override file";
-
-'D':
-	optional, mergeable, detailedonly, pattern, values: 1,
-	'<value>',
-	"generic property override";
-
-'exit':
-	optional, detailedonly, values: 0,
-	"use System.exit() on termination";
-
-'verbose':
-	optional, detailedonly, values: 0,
-	excludes {'silent', 'quiet', 'debug'},
-	"verbose output operation";
-
-'quiet':
-	optional, detailedonly, values: 0,
-	excludes {'silent', 'verbose', 'debug'},
-	"quiet operation (ignore all but warnings and severe errors)";
-
-'silent':
-	optional, detailedonly, values: 0,
-	excludes {'quiet', 'verbose', 'debug'},
-	"extra-quiet operation (ignore all but severe errors)";
-
-'debug', 'loglevel': 
-	optional, detailedonly, values: ?,
-	'[<debug trace level>]',
-	excludes {'verbose', 'quiet', 'silent'},
-	"debug tracing level";
-
-'debugcls':
-	optional, detailedonly, values: 1,
-	'<debug trace class mask>',
-	"class mask for debug tracing";
-
-
diff --git a/core/res/emma_ant.properties b/core/res/emma_ant.properties
deleted file mode 100644
index 7fca4c0..0000000
--- a/core/res/emma_ant.properties
+++ /dev/null
@@ -1,7 +0,0 @@
-# -------------------------------------------------------------
-
-emma:		com.vladium.emma.emmaTask
-emmajava:	com.vladium.emma.emmajavaTask
-
-# -------------------------------------------------------------
-# end of file
diff --git a/core/res/emma_default.properties b/core/res/emma_default.properties
deleted file mode 100644
index bbba41d..0000000
--- a/core/res/emma_default.properties
+++ /dev/null
@@ -1,91 +0,0 @@
-# -------------------------------------------------------------
-# *************** DO NOT EDIT THIS FILE ***********************
-#
-# for user-editable property overrides use one of these options:
-#
-# (1) option-specific command line overrides, e.g.
-#     -Dreport.txt.out.file=coverage.txt
-#
-# (2) '-p <options file>' command line option,
-#
-# (3) 'emma.properties' resource placed somewhere in the classpath
-#     (e.g., in <jre dir>\classes directory -- note that it does
-#     not exist by default),
-#
-# (4) '-Demma.*' JVM options, e.g.
-#     -Demma.report.txt.out.file=coverage.txt
-#
-# (5) 'emma.properties' JVM option pointing to a properties file
-#     -Demma.properties=./myproperties.txt
-# -------------------------------------------------------------
-
-# -------------------------------------------------------------
-# logging properties:
-
-verbosity.level:	info
-
-# classloading properties:
-
-#clsload.forced_delegation_filter:
-#clsload.through_delegation_filter: -*
-
-# -------------------------------------------------------------
-
-# instrumentation properties:
-
-instr.exclude_synthetic_methods:	true
-instr.exclude_bridge_methods:		true
-instr.do_suid_compensation:		true
-
-# -------------------------------------------------------------
-
-# apprunner session data output properties:
-
-session.out.file:	coverage.es
-session.out.merge:	true
-
-# -------------------------------------------------------------
-
-# runtime coverage data output properties:
-
-coverage.out.file:	/sdcard/coverage.ec
-coverage.out.merge:	true
-
-# -------------------------------------------------------------
-
-# instr metadata output properties:
-
-metadata.out.file:	coverage.em
-metadata.out.merge:	true
-
-# -------------------------------------------------------------
-
-# common report defaults:
-
-report.units:		instr
-report.depth:		method
-report.columns:		name,class,method,block,line
-report.sort:		+block,+name,+method,+class
-report.metrics:		method:70,block:80,line:80,class:100
-
-# -------------------------------------------------------------
-# txt report properties:
-
-report.txt.depth:	all
-report.txt.columns:	class,method,block,line,name
-report.txt.out.file:	coverage.txt
-
-# -------------------------------------------------------------
-# html report properties:
-
-#report.html.out.dir:	coverage
-report.html.out.file:	coverage/index.html
-report.html.out.encoding: ISO-8859-1
-
-# -------------------------------------------------------------
-# xml report properties:
-
-report.xml.out.file:	coverage.xml
-report.xml.out.encoding: UTF-8
-# -------------------------------------------------------------
-# end of file
diff --git a/cpl-v10.html b/cpl-v10.html
deleted file mode 100644
index 36aa208..0000000
--- a/cpl-v10.html
+++ /dev/null
@@ -1,125 +0,0 @@
-<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0//EN">
-<HTML>
-<HEAD>
-<TITLE>Common Public License - v 1.0</TITLE>
-<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1">
-</HEAD>
-
-<BODY BGCOLOR="#FFFFFF" VLINK="#800000">
-
-
-<P ALIGN="CENTER"><B>Common Public License - v 1.0</B>
-<P><B></B><FONT SIZE="3"></FONT>
-<P><FONT SIZE="3"></FONT><FONT SIZE="2">THE ACCOMPANYING PROGRAM IS PROVIDED UNDER THE TERMS OF THIS COMMON PUBLIC LICENSE ("AGREEMENT").  ANY USE, REPRODUCTION OR DISTRIBUTION OF THE PROGRAM CONSTITUTES RECIPIENT'S ACCEPTANCE OF THIS AGREEMENT.</FONT>
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2"><B>1.  DEFINITIONS</B></FONT>
-<P><FONT SIZE="2">"Contribution" means:</FONT>
-
-<UL><FONT SIZE="2">a) in the case of the initial Contributor, the initial code and documentation distributed under this Agreement, and<BR CLEAR="LEFT">
-b) in the case of each subsequent Contributor:</FONT></UL>
-
-
-<UL><FONT SIZE="2">i)	 	changes to the Program, and</FONT></UL>
-
-
-<UL><FONT SIZE="2">ii)		additions to the Program;</FONT></UL>
-
-
-<UL><FONT SIZE="2">where such changes and/or additions to the Program originate from and are distributed by that particular Contributor.  </FONT><FONT SIZE="2">A Contribution 'originates' from a Contributor if it was added to the Program by such Contributor itself or anyone acting on such Contributor's behalf.  </FONT><FONT SIZE="2">Contributions do not include additions to the Program which:  (i) are separate modules of software distributed in conjunction with the Program under their own license agreement, and (ii) are not derivative works of the Program.  </FONT></UL>
-
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2">"Contributor" means any person or entity that distributes the Program.</FONT>
-<P><FONT SIZE="2"></FONT><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2">"Licensed Patents " mean patent claims licensable by a Contributor which are necessarily infringed by the use or sale of its Contribution alone or when combined with the Program.  </FONT>
-<P><FONT SIZE="2"></FONT><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2"></FONT><FONT SIZE="2">"Program" means the Contributions distributed in accordance with this Agreement.</FONT>
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2">"Recipient" means anyone who receives the Program under this Agreement, including all Contributors.</FONT>
-<P><FONT SIZE="2"><B></B></FONT>
-<P><FONT SIZE="2"><B>2.  GRANT OF RIGHTS</B></FONT>
-
-<UL><FONT SIZE="2"></FONT><FONT SIZE="2">a)	</FONT><FONT SIZE="2">Subject to the terms of this Agreement, each Contributor hereby grants</FONT><FONT SIZE="2"> Recipient a non-exclusive, worldwide, royalty-free copyright license to</FONT><FONT SIZE="2" COLOR="#FF0000"> </FONT><FONT SIZE="2">reproduce, prepare derivative works of, publicly display, publicly perform, distribute and sublicense the Contribution of such Contributor, if any, and such derivative works, in source code and object code form.</FONT></UL>
-
-
-<UL><FONT SIZE="2"></FONT></UL>
-
-
-<UL><FONT SIZE="2"></FONT><FONT SIZE="2">b) 	Subject to the terms of this Agreement, each Contributor hereby grants </FONT><FONT SIZE="2">Recipient a non-exclusive, worldwide,</FONT><FONT SIZE="2" COLOR="#008000"> </FONT><FONT SIZE="2">royalty-free patent license under Licensed Patents to make, use, sell, offer to sell, import and otherwise transfer the Contribution of such Contributor, if any, in source code and object code form.  This patent license shall apply to the combination of the Contribution and the Program if, at the time the Contribution is added by the Contributor, such addition of the Contribution causes such combination to be covered by the Licensed Patents.  The patent license shall not apply to any other combinations which include the Contribution.  No hardware per se is licensed hereunder.   </FONT></UL>
-
-
-<UL><FONT SIZE="2"></FONT></UL>
-
-
-<UL><FONT SIZE="2">c)	Recipient understands that although each Contributor grants the licenses to its Contributions set forth herein, no assurances are provided by any Contributor that the Program does not infringe the patent or other intellectual property rights of any other entity.  Each Contributor disclaims any liability to Recipient for claims brought by any other entity based on infringement of intellectual property rights or otherwise.  As a condition to exercising the rights and licenses granted hereunder, each Recipient hereby assumes sole responsibility to secure any other intellectual property rights needed, if any.  For example, if a third party patent license is required to allow Recipient to distribute the Program, it is Recipient's responsibility to acquire that license before distributing the Program.</FONT></UL>
-
-
-<UL><FONT SIZE="2"></FONT></UL>
-
-
-<UL><FONT SIZE="2">d)	Each Contributor represents that to its knowledge it has sufficient copyright rights in its Contribution, if any, to grant the copyright license set forth in this Agreement. </FONT></UL>
-
-
-<UL><FONT SIZE="2"></FONT></UL>
-
-<P><FONT SIZE="2"><B>3.  REQUIREMENTS</B></FONT>
-<P><FONT SIZE="2"><B></B>A Contributor may choose to distribute the Program in object code form under its own license agreement, provided that:</FONT>
-
-<UL><FONT SIZE="2">a)	it complies with the terms and conditions of this Agreement; and</FONT></UL>
-
-
-<UL><FONT SIZE="2">b)	its license agreement:</FONT></UL>
-
-
-<UL><FONT SIZE="2">i)	effectively disclaims</FONT><FONT SIZE="2"> on behalf of all Contributors all warranties and conditions, express and implied, including warranties or conditions of title and non-infringement, and implied warranties or conditions of merchantability and fitness for a particular purpose; </FONT></UL>
-
-
-<UL><FONT SIZE="2">ii) 	effectively excludes on behalf of all Contributors all liability for damages, including direct, indirect, special, incidental and consequential damages, such as lost profits; </FONT></UL>
-
-
-<UL><FONT SIZE="2">iii)</FONT><FONT SIZE="2">	states that any provisions which differ from this Agreement are offered by that Contributor alone and not by any other party; and</FONT></UL>
-
-
-<UL><FONT SIZE="2">iv)	states that source code for the Program is available from such Contributor, and informs licensees how to obtain it in a reasonable manner on or through a medium customarily used for software exchange.</FONT><FONT SIZE="2" COLOR="#0000FF"> </FONT><FONT SIZE="2" COLOR="#FF0000"></FONT></UL>
-
-
-<UL><FONT SIZE="2" COLOR="#FF0000"></FONT><FONT SIZE="2"></FONT></UL>
-
-<P><FONT SIZE="2">When the Program is made available in source code form:</FONT>
-
-<UL><FONT SIZE="2">a)	it must be made available under this Agreement; and </FONT></UL>
-
-
-<UL><FONT SIZE="2">b)	a copy of this Agreement must be included with each copy of the Program.  </FONT></UL>
-
-<P><FONT SIZE="2"></FONT><FONT SIZE="2" COLOR="#0000FF"><STRIKE></STRIKE></FONT>
-<P><FONT SIZE="2" COLOR="#0000FF"><STRIKE></STRIKE></FONT><FONT SIZE="2">Contributors may not remove or alter any copyright notices contained within the Program.  </FONT>
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2">Each Contributor must identify itself as the originator of its Contribution, if any, in a manner that reasonably allows subsequent Recipients to identify the originator of the Contribution.  </FONT>
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2"><B>4.  COMMERCIAL DISTRIBUTION</B></FONT>
-<P><FONT SIZE="2">Commercial distributors of software may accept certain responsibilities with respect to end users, business partners and the like.  While this license is intended to facilitate the commercial use of the Program, the Contributor who includes the Program in a commercial product offering should do so in a manner which does not create potential liability for other Contributors.   Therefore, if a Contributor includes the Program in a commercial product offering, such Contributor ("Commercial Contributor") hereby agrees to defend and indemnify every other Contributor ("Indemnified Contributor") against any losses, damages and costs (collectively "Losses") arising from claims, lawsuits and other legal actions brought by a third party against the Indemnified Contributor to the extent caused by the acts or omissions of such Commercial Contributor in connection with its distribution of the Program in a commercial product offering.  The obligations in this section do not apply to any claims or Losses relating to any actual or alleged intellectual property infringement.  In order to qualify, an Indemnified Contributor must: a) promptly notify the Commercial Contributor in writing of such claim, and b) allow the Commercial Contributor to control, and cooperate with the Commercial Contributor in, the defense and any related settlement negotiations.  The Indemnified Contributor may participate in any such claim at its own expense.</FONT>
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2">For example, a Contributor might include the Program in a commercial product offering, Product X.  That Contributor is then a Commercial Contributor.  If that Commercial Contributor then makes performance claims, or offers warranties related to Product X, those performance claims and warranties are such Commercial Contributor's responsibility alone.  Under this section, the Commercial Contributor would have to defend claims against the other Contributors related to those performance claims and warranties, and if a court requires any other Contributor to pay any damages as a result, the Commercial Contributor must pay those damages.</FONT>
-<P><FONT SIZE="2"></FONT><FONT SIZE="2" COLOR="#0000FF"></FONT>
-<P><FONT SIZE="2" COLOR="#0000FF"></FONT><FONT SIZE="2"><B>5.  NO WARRANTY</B></FONT>
-<P><FONT SIZE="2">EXCEPT AS EXPRESSLY SET FORTH IN THIS AGREEMENT, THE PROGRAM IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED INCLUDING, WITHOUT LIMITATION, ANY WARRANTIES OR CONDITIONS OF TITLE, NON-INFRINGEMENT, MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. Each Recipient is</FONT><FONT SIZE="2"> solely responsible for determining the appropriateness of using and distributing </FONT><FONT SIZE="2">the Program</FONT><FONT SIZE="2"> and assumes all risks associated with its exercise of rights under this Agreement</FONT><FONT SIZE="2">, including but not limited to the risks and costs of program errors, compliance with applicable laws, damage to or loss of data, </FONT><FONT SIZE="2">programs or equipment, and unavailability or interruption of operations</FONT><FONT SIZE="2">.  </FONT><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2"></FONT><FONT SIZE="2"><B>6.  DISCLAIMER OF LIABILITY</B></FONT>
-<P><FONT SIZE="2"></FONT><FONT SIZE="2">EXCEPT AS EXPRESSLY SET FORTH IN THIS AGREEMENT, NEITHER RECIPIENT NOR ANY CONTRIBUTORS SHALL HAVE ANY LIABILITY FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES </FONT><FONT SIZE="2">(INCLUDING WITHOUT LIMITATION LOST PROFITS),</FONT><FONT SIZE="2"> HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OR DISTRIBUTION OF THE PROGRAM OR THE EXERCISE OF ANY RIGHTS GRANTED HEREUNDER, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.</FONT>
-<P><FONT SIZE="2"></FONT><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2"><B>7.  GENERAL</B></FONT>
-<P><FONT SIZE="2"></FONT><FONT SIZE="2">If any provision of this Agreement is invalid or unenforceable under applicable law, it shall not affect the validity or enforceability of the remainder of the terms of this Agreement, and without further action by the parties hereto, such provision shall be reformed to the minimum extent necessary to make such provision valid and enforceable.</FONT>
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2">If Recipient institutes patent litigation against a Contributor with respect to a patent applicable to software (including a cross-claim or counterclaim in a lawsuit), then any patent licenses granted by that Contributor to such Recipient under this Agreement shall terminate as of the date such litigation is filed.  In addition, if Recipient institutes patent litigation against any entity (including a cross-claim or counterclaim in a lawsuit) alleging that the Program itself (excluding combinations of the Program with other software or hardware) infringes such Recipient's patent(s), then such Recipient's rights granted under Section 2(b) shall terminate as of the date such litigation is filed. </FONT><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2">All Recipient's rights under this Agreement shall terminate if it fails to comply with any of the material terms or conditions of this Agreement and does not cure such failure in a reasonable period of time after becoming aware of such noncompliance.  If all Recipient's rights under this Agreement terminate, Recipient agrees to cease use and distribution of the Program as soon as reasonably practicable.  However, Recipient's obligations under this Agreement and any licenses granted by Recipient relating to the Program shall continue and survive.  </FONT><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2"></FONT><FONT SIZE="2">Everyone is permitted to copy and distribute copies of this Agreement, but in order to avoid inconsistency the Agreement is copyrighted  and may only be modified in the following manner. The Agreement Steward reserves the right to </FONT><FONT SIZE="2">publish new versions (including revisions) of this Agreement from time to </FONT><FONT SIZE="2">time. No one other than the Agreement Steward has the right to modify this Agreement. IBM is the initial Agreement Steward.   IBM may assign the responsibility to serve as the Agreement Steward to a suitable separate entity.  </FONT><FONT SIZE="2">Each new version of the Agreement will be given a distinguishing version number.  The Program (including Contributions) may always be distributed subject to the version of the Agreement under which it was received. In addition, after a new version of the Agreement is published, Contributor may elect to distribute the Program (including its Contributions) under the new </FONT><FONT SIZE="2">version.  </FONT><FONT SIZE="2">Except as expressly stated in Sections 2(a) and 2(b) above, Recipient receives no rights or licenses to the intellectual property of any Contributor under this Agreement, whether expressly, </FONT><FONT SIZE="2">by implication, estoppel or otherwise</FONT><FONT SIZE="2">.</FONT><FONT SIZE="2">  All rights in the Program not expressly granted under this Agreement are reserved.</FONT>
-<P><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2">This Agreement is governed by the laws of the State of New York and the intellectual property laws of the United States of America. No party to this Agreement will bring a legal action under this Agreement more than one year after the cause of action arose.  Each party waives its rights to a jury trial in any resulting litigation.</FONT>
-<P><FONT SIZE="2"></FONT><FONT SIZE="2"></FONT>
-<P><FONT SIZE="2"></FONT>
-
-</BODY>
-
-</HTML>
\ No newline at end of file
diff --git a/dependencies.xml b/dependencies.xml
deleted file mode 100644
index 77ccad7..0000000
--- a/dependencies.xml
+++ /dev/null
@@ -1,117 +0,0 @@
-  <!-- ============================================================== -->
-
-  <patternset id="java.libs" includes="*.jar,*.zip" /> <!-- not recursing by design -->
-
-
-  <!-- ANT 1.4.x dependency: -->
-  <path id="boot.ant.14.classpath" >
-    <pathelement location="${build.target.ant.14.home}/lib/ant.jar" />
-  </path>
-
-  <!-- ANT 1.5.x dependency: -->
-  <path id="boot.ant.15.classpath" >
-    <pathelement location="${build.target.ant.15.home}/lib/ant.jar" />
-  </path>
-
-
-  <!-- J2SE 1.2 boot classpath: -->
-  <path id="boot.j2se.12.classpath" >
-    <fileset dir="${build.target.j2se.12.home}/lib/" >
-      <patternset refid="java.libs" />
-    </fileset>
-  </path>
-
-  <!-- J2SE 1.2 ext classpath: -->
-  <property name="ext.j2se.12.classpath"
-    value="${build.target.j2se.12.home}/lib/ext/"
-  />
-
-
-  <!-- J2SE 1.3 boot classpath: -->
-  <path id="boot.j2se.13.classpath" >
-    <fileset dir="${build.target.j2se.13.home}/lib/" >
-      <patternset refid="java.libs" />
-    </fileset>
-  </path>
-
-  <!-- J2SE 1.3 ext classpath: -->
-  <property name="ext.j2se.13.classpath"
-    value="${build.target.j2se.13.home}/lib/ext/"
-  />
-
-
-  <!-- J2SE 1.4 boot classpath: -->
-  <path id="boot.j2se.14.classpath" >
-    <fileset dir="${build.target.j2se.14.home}/lib/" >
-      <patternset refid="java.libs" />
-    </fileset>
-  </path>
-
-  <!-- J2SE 1.4 ext classpath: -->
-  <property name="ext.j2se.14.classpath"
-    value="${build.target.j2se.14.home}/lib/ext/"
-  />
-
-  <!-- ============================================================== -->
-  <!-- lib module: -->
-
-  <!-- 3rd party dependencies: -->
-  <path id="lib.external.classpath" >
-    <fileset dir="${external.lib.dir}" >
-      <patternset refid="java.libs" />
-    </fileset>
-  </path>
-
-  <!-- internal dependencies: -->
-  <path id="lib.internal.classpath" >
-    <fileset dir="${internal.lib.dir}" >
-      <patternset refid="java.libs" />
-    </fileset>
-  </path>
-
-  <!-- complete dependency classpath: -->
-  <path id="lib.classpath" >
-    <path refid="lib.internal.classpath" />
-    <path refid="lib.external.classpath" />
-  </path>
-
-  <!-- ============================================================== -->
-  <!-- core module: -->
-
-  <!-- compiled module classes + res + lib.classpath: -->
-  <path id="core.classpath" >
-    <pathelement location="${core.classes.out.dir}" />
-    <pathelement location="${core.res.dir}" />
-    <path refid="lib.classpath" />
-  </path>
-
-  <!-- ============================================================== -->
-  <!-- ant module: -->
-
-  <!-- compiled module classes + res + +ant classpath + core.classpath: -->
-  <path id="ant.14.classpath" >
-    <pathelement location="${ant.classes.out.dir}" />
-    <pathelement location="${ant.res.dir}" />
-    <path refid="core.classpath" />
-    <path refid="boot.ant.14.classpath" />
-  </path>
-
-  <!-- compiled module classes + res + +ant classpath + core.classpath: -->
-  <path id="ant.15.classpath" >
-    <pathelement location="${ant.classes.out.dir}" />
-    <pathelement location="${ant.res.dir}" />
-    <path refid="core.classpath" />
-    <path refid="boot.ant.15.classpath" />
-  </path>
-
-  <!-- ============================================================== -->
-  <!-- tools module: -->
-
-  <!-- compiled module classes + res + core.classpath: -->
-  <path id="tools.classpath" >
-    <pathelement location="${tools.classes.out.dir}" />
-    <pathelement location="${tools.res.dir}" />
-    <path refid="core.classpath" />
-  </path>
-
-  <!-- ========== END OF FILE ======================================= -->
diff --git a/lib/emma.jar b/lib/emma.jar
deleted file mode 100644
index 27629de..0000000
--- a/lib/emma.jar
+++ /dev/null
Binary files differ
diff --git a/lib/emma_ant.jar b/lib/emma_ant.jar
deleted file mode 100644
index 3f28c2c..0000000
--- a/lib/emma_ant.jar
+++ /dev/null
Binary files differ
diff --git a/lib/external/placeholder.exclude b/lib/external/placeholder.exclude
deleted file mode 100644
index e69de29..0000000
--- a/lib/external/placeholder.exclude
+++ /dev/null
diff --git a/lib/internal/placeholder.exclude b/lib/internal/placeholder.exclude
deleted file mode 100644
index e69de29..0000000
--- a/lib/internal/placeholder.exclude
+++ /dev/null
diff --git a/lib/internal/stamptool.jar b/lib/internal/stamptool.jar
deleted file mode 100644
index 1f8f089..0000000
--- a/lib/internal/stamptool.jar
+++ /dev/null
Binary files differ
diff --git a/module.dirs.properties b/module.dirs.properties
deleted file mode 100644
index 90fc1c2..0000000
--- a/module.dirs.properties
+++ /dev/null
@@ -1,79 +0,0 @@
-# -----------------------------------------------------------------------------
-# misc aliases:
-
-tools:                                          tools
-core:                                           core
-ant:                                            ant
-test:                                           test
-
-lib:                                            lib
-data:                                           data
-res:                                            res
-
-java:                                           java
-java12:                                         java12
-java13:                                         java13
-java14:                                         java14
-
-ant14:                                          ant14
-ant15:                                          ant15
-
-internal:                                       internal
-external:                                       external
-
-# -----------------------------------------------------------------------------
-# ---- module-specific static (checked-in) locations:
-
-# -----------------------------------------------------------------------------
-# lib module structure:
-
-lib.dir.root:                                   ${basedir}/${lib}
-
-internal.lib.dir:                               ${lib.dir.root}/${internal}
-external.lib.dir:                               ${lib.dir.root}/${external}
-
-# -----------------------------------------------------------------------------
-# core module structure:
-
-core.dir.root:                                  ${basedir}/${core}
-
-core.src.java12.dir:                            ${core.dir.root}/${java12}
-core.src.java13.dir:                            ${core.dir.root}/${java13}
-core.src.java14.dir:                            ${core.dir.root}/${java14}
-
-core.res.dir:                                   ${core.dir.root}/${res}
-core.data.dir:                                  ${core.dir.root}/${data}
-
-# -----------------------------------------------------------------------------
-# ant module structure:
-
-ant.dir.root:                                   ${basedir}/${ant}
-
-ant.src.ant14.dir:                              ${ant.dir.root}/${ant14}
-ant.src.ant15.dir:                              ${ant.dir.root}/${ant15}
-
-ant.res.dir:                                    ${ant.dir.root}/${res}
-ant.data.dir:                                   ${ant.dir.root}/${data}
-
-# -----------------------------------------------------------------------------
-# tools module structure:
-
-tools.dir.root:                                 ${basedir}/${tools}
-
-tools.src.dir:                                  ${tools.dir.root}/${java}
-
-tools.res.dir:                                  ${tools.dir.root}/${res}
-tools.data.dir:                                 ${tools.dir.root}/${data}
-
-# -----------------------------------------------------------------------------
-# test module structure:
-
-test.dir.root:                                   ${basedir}/${test}
-
-test.src.dir:                                    ${test.dir.root}/${java}
-
-test.res.dir:                                    ${test.dir.root}/${res}
-test.data.dir:                                   ${test.dir.root}/${data}
-
-# -----------------------------------------------------------------------------
-# end of file
diff --git a/release.properties b/release.properties
deleted file mode 100644
index d27d234..0000000
--- a/release.properties
+++ /dev/null
@@ -1,19 +0,0 @@
-# -----------------------------------------------------------------------------
-
-# properties that control release major.minor labeling:
-
-app.major.version:	2
-app.minor.version:	0
-
-# properties affecting formatting of build id and date:
-
-app.build.id.format:	~Md~
-app.build.date.format:	~D T~
-
-# string used in the HTML content:
-
-app.bug.report.link:	http://sourceforge.net/projects/${app.short.name}
-app.home.site.link:		http://${app.short.name}.sourceforge.net/
-
-# -----------------------------------------------------------------------------
-# end of file
diff --git a/tools/java/com/vladium/tools/ClassDep.java b/tools/java/com/vladium/tools/ClassDep.java
deleted file mode 100644
index 05d06b9..0000000
--- a/tools/java/com/vladium/tools/ClassDep.java
+++ /dev/null
@@ -1,220 +0,0 @@
-/* Copyright (C) 2004 Vladimir Roubtsov. All rights reserved.
- * 
- * This program and the accompanying materials are made available under
- * the terms of the Common Public License v1.0 which accompanies this distribution,
- * and is available at http://www.eclipse.org/legal/cpl-v10.html
- * 
- * $Id: ClassDep.java,v 1.1.2.2 2004/07/09 01:42:04 vlad_r Exp $
- */
-package com.vladium.tools;
-
-import java.io.File;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.net.URL;
-import java.net.URLClassLoader;
-import java.util.ArrayList;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.LinkedList;
-import java.util.List;
-import java.util.Properties;
-import java.util.Set;
-import java.util.StringTokenizer;
-
-import com.vladium.jcd.cls.ClassDef;
-import com.vladium.jcd.cls.IConstantCollection;
-import com.vladium.jcd.cls.constant.CONSTANT_Class_info;
-import com.vladium.jcd.cls.constant.CONSTANT_info;
-import com.vladium.jcd.parser.ClassDefParser;
-import com.vladium.util.ByteArrayOStream;
-import com.vladium.util.Descriptors;
-
-// ----------------------------------------------------------------------------
-/**
- * TODO: doc
- * 
- * @author Vlad Roubtsov, (C) 2004
- */
-public class ClassDep
-{
-    // public: ................................................................
-    
-    public static void main (final String [] args)
-        throws Exception
-    {
-        if (args.length < 2)
-            throw new IllegalArgumentException ("usage: classpath output_file rootset_classname_1 [rootset_classname_2 ...]");
-            
-        final String _classPath = args [0];
-        final URL [] classPath;
-        {
-            final StringTokenizer tokenizer = new StringTokenizer (_classPath, File.pathSeparator);
-            classPath = new URL [tokenizer.countTokens ()];
-            
-            for (int i = 0; tokenizer.hasMoreTokens (); ++ i)
-            {
-                classPath [i] = new File (tokenizer.nextToken ()).toURL ();
-            }
-        }
-        
-        final File outFile = new File (args [1]);
-        
-        final int offset = 2;
-        final String [] rootSet = args.length > offset
-            ? new String [args.length - offset]
-            : new String [0];
-        {
-            for (int a = 0; a < rootSet.length; ++ a)
-            {
-                rootSet [a] = args [a + offset];
-            }
-        }
-        
-        final ClassDep _this = new ClassDep (rootSet, classPath);
-        final String [] deps = _this.getDependencies (true);
-        
-        final StringBuffer s = new StringBuffer (); 
-        for (int d = deps.length - 1; d >= 0; -- d) // reverse topological order
-        {
-            s.append (deps [d]);
-            if (d > 0) s.append (',');
-        }
-        
-        final File parent = outFile.getParentFile ();
-        if (parent != null) parent.mkdirs ();
-        
-        final FileOutputStream out = new FileOutputStream (outFile);
-        
-        final Properties result = new Properties ();
-        result.setProperty ("closure", s.toString ());
-        
-        result.store (out, "this file is auto-generated, do not edit");
-        
-        out.close ();
-    }
-    
-    
-    public ClassDep (final String [] rootSet, final URL [] classPath)
-    {
-        if (rootSet == null)
-            throw new IllegalArgumentException ("null input: rootSet");
-        
-        if (classPath == null)
-            throw new IllegalArgumentException ("null input: classPath");
-        
-        m_rootSet = rootSet;
-        m_classPath = classPath;
-    }
-    
-    public String [] getDependencies (final boolean includeRootSet)
-        throws IOException
-    {
-        final Set /* class Java name:String */ _result = new HashSet ();
-        final ClassLoader loader = new URLClassLoader (m_classPath, null);
-        
-        if (includeRootSet)
-        {
-            for (int i = 0; i < m_rootSet.length; ++ i)
-            {
-                _result.add (m_rootSet [i]);
-            }
-        }
-        
-        final LinkedList /* class VM name:String */ queue = new LinkedList ();
-        for (int i = 0; i < m_rootSet.length; ++ i)
-        {
-            queue.add (Descriptors.javaNameToVMName (m_rootSet [i]));
-        }
-        
-        final ByteArrayOStream baos = new ByteArrayOStream (8 * 1024);
-        final byte [] readbuf = new byte [8 * 1024];
-        
-        while (! queue.isEmpty ())
-        {
-            final String classVMName = (String) queue.removeFirst ();
-            
-            // keep at most one file descriptor open:
-            
-            InputStream in = null;
-            try
-            {
-                // NOTE: getResources() not used
-                in = loader.getResourceAsStream (classVMName + ".class");
-                
-                if (in == null)
-                {
-                    throw new IllegalArgumentException ("class [" + Descriptors.vmNameToJavaName (classVMName) + "] not found in the input classpath");
-                }
-                else
-                {
-                    baos.reset ();
-                    for (int read; (read = in.read (readbuf)) >= 0; baos.write (readbuf, 0, read));
-                }
-            }
-            finally
-            {
-                if (in != null) try { in.close (); } catch (IOException ignore) { ignore.printStackTrace (); }
-            }
-            in = null;
-
-            final ClassDef cls = ClassDefParser.parseClass (baos.getByteArray (), baos.size ());
-            final List /* class VM name:String */ clsDeps  = getCONSTANT_Class_info (cls);
-            
-            for (Iterator i = clsDeps.iterator (); i.hasNext (); )
-            {
-                final String classDepVMName = (String) i.next ();
-                
-                if (classDepVMName.startsWith ("com/vladium/")) // TODO: generic filtering
-                {
-                    if (_result.add (Descriptors.vmNameToJavaName (classDepVMName)))
-                    {
-                        queue.addLast (classDepVMName);
-                    }
-                }
-            }
-        }
-        
-        final String [] result = new String [_result.size ()];
-        _result.toArray (result);
-        
-        return result;
-    }
-    
-    /**
-     * @return array of class VM names [may contain duplicates]
-     */
-    public static List getCONSTANT_Class_info (final ClassDef cls)
-    {
-        if (cls == null)
-            throw new IllegalArgumentException ("null input: cls");
-        
-        final IConstantCollection constants = cls.getConstants ();
-        final IConstantCollection.IConstantIterator i = constants.iterator ();
-        
-        final List result = new ArrayList ();
-
-        for (CONSTANT_info entry; (entry = i.nextConstant ()) != null; )
-        {
-            if (entry instanceof CONSTANT_Class_info)
-            {
-                result.add (((CONSTANT_Class_info) entry).getName (cls));
-            }
-        }
-        
-        return result;
-    }
-    
-    // protected: .............................................................
-
-    // package: ...............................................................
-    
-    // private: ...............................................................
-
-
-    private final String [] m_rootSet;
-    private final URL [] m_classPath;
-    
-} // end of class
-// ----------------------------------------------------------------------------
\ No newline at end of file
diff --git a/work.dirs.properties b/work.dirs.properties
deleted file mode 100644
index e215fa1..0000000
--- a/work.dirs.properties
+++ /dev/null
@@ -1,52 +0,0 @@
-# -----------------------------------------------------------------------------
-# misc aliases:
-
-classes:                                        classes
-files:                                          files
-srcgen:                                         srcgen
-
-# -----------------------------------------------------------------------------
-# ---- root locations created by the build:
-
-# root dir of all build output:
-out.dir:                                        ${basedir}/out
-
-# distribution dir:
-dist.dir:                                       ${basedir}/dist
-
-# distribution dir:
-release.dir:                                    ${basedir}/release
-
-# directory for scratch files:
-temp.dir:                                       ${out.dir}/temp
-
-# -----------------------------------------------------------------------------
-# ---- module-specific locations created by the build:
-
-# -----------------------------------------------------------------------------
-# core module:
-
-core.classes.out.dir:                           ${out.dir}/${core}/${classes}
-core.srcgen.out.dir:                            ${out.dir}/${core}/${srcgen}
-core.res.out.dir:                               ${out.dir}/${core}/${res}
-
-# -----------------------------------------------------------------------------
-# ant module:
-
-ant.classes.out.dir:                            ${out.dir}/${ant}/${classes}
-ant.srcgen.out.dir:                             ${out.dir}/${ant}/${srcgen}
-
-# -----------------------------------------------------------------------------
-# tools module:
-
-tools.classes.out.dir:                          ${out.dir}/${tools}/${classes}
-tools.srcgen.out.dir:                           ${out.dir}/${tools}/${srcgen}
-
-# -----------------------------------------------------------------------------
-# test module:
-
-test.classes.out.dir:                           ${out.dir}/${test}/${classes}
-test.srcgen.out.dir:                            ${out.dir}/${test}/${srcgen}
-
-# -----------------------------------------------------------------------------
-# end of file
