Author: schor
Date: Fri Jul 17 21:03:03 2015
New Revision: 1691640

URL: http://svn.apache.org/r1691640
Log:
[UIMA-4518] add decompiler for JCas cover classes, and tool to scan these and 
identify customized ones.

Added:
    
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcas/
    
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcas/internal/
    
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcas/internal/AnalyzeContent.java
    
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcasgen/DecompiledFilter.java
Modified:
    
uima/uimaj/branches/experiment-v3-jcas/uimaj-core/src/main/java/org/apache/uima/cas/impl/TypeSystemImpl.java
    
uima/uimaj/branches/experiment-v3-jcas/uimaj-core/src/main/java/org/apache/uima/jcas/impl/JCasImpl.java
    
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcasgen/Jg.java

Modified: 
uima/uimaj/branches/experiment-v3-jcas/uimaj-core/src/main/java/org/apache/uima/cas/impl/TypeSystemImpl.java
URL: 
http://svn.apache.org/viewvc/uima/uimaj/branches/experiment-v3-jcas/uimaj-core/src/main/java/org/apache/uima/cas/impl/TypeSystemImpl.java?rev=1691640&r1=1691639&r2=1691640&view=diff
==============================================================================
--- 
uima/uimaj/branches/experiment-v3-jcas/uimaj-core/src/main/java/org/apache/uima/cas/impl/TypeSystemImpl.java
 (original)
+++ 
uima/uimaj/branches/experiment-v3-jcas/uimaj-core/src/main/java/org/apache/uima/cas/impl/TypeSystemImpl.java
 Fri Jul 17 21:03:03 2015
@@ -33,14 +33,23 @@ import static org.apache.uima.cas.impl.S
 import static org.apache.uima.cas.impl.SlotKinds.SlotKind.Slot_StrRef;
 import static org.apache.uima.cas.impl.SlotKinds.SlotKind.Slot_TypeCode;
 
+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.util.ArrayList;
 import java.util.Arrays;
 import java.util.BitSet;
 import java.util.HashMap;
+import java.util.HashSet;
 import java.util.Iterator;
 import java.util.List;
 import java.util.Map;
 import java.util.NoSuchElementException;
+import java.util.Set;
 import java.util.Vector;
 import java.util.WeakHashMap;
 
@@ -57,7 +66,13 @@ import org.apache.uima.internal.util.Str
 import org.apache.uima.internal.util.SymbolTable;
 import org.apache.uima.internal.util.rb_trees.IntRedBlackTree;
 import org.apache.uima.internal.util.rb_trees.RedBlackTree;
+import org.apache.uima.jcas.impl.JCasImpl;
 import org.apache.uima.resource.ResourceInitializationException;
+import org.apache.uima.util.Misc;
+
+import com.strobel.decompiler.Decompiler;
+import com.strobel.decompiler.DecompilerSettings;
+import com.strobel.decompiler.PlainTextOutput;
 
 /**
  * Type system implementation.
@@ -70,6 +85,9 @@ import org.apache.uima.resource.Resource
  */
 public class TypeSystemImpl implements TypeSystemMgr, LowLevelTypeSystem {
   
+  private final static String DECOMPILE_JCAS = "uima.decompile.jcas";
+  private final static boolean IS_DECOMPILE_JCAS = 
Misc.getNoValueSystemProperty(DECOMPILE_JCAS);
+  
   private final static int[] INT0 = new int[0];
   
   private final static IntVector zeroLengthIntVector = new IntVector(1);  // 
capacity is 1; 0 makes length default to 16
@@ -145,6 +163,10 @@ public class TypeSystemImpl implements T
     arrayTypeComponentNameMap.put(CAS.TYPE_NAME_STRING_ARRAY, 
CAS.TYPE_NAME_STRING);
   }
 
+  private final static Set<String> decompiled = (IS_DECOMPILE_JCAS) ? new 
HashSet<String>(256) : null;
+
+  private static final Object GLOBAL_TYPESYS_LOCK = new Object();
+
   // Current implementation has online update. Look-up could be made
   // more efficient by computing some tables, but the assumption is
   // that the type system will not be queried often enough to justify
@@ -237,6 +259,8 @@ public class TypeSystemImpl implements T
   // must be volatile to force the right memory barriers
   volatile boolean areBuiltInTypesSetup = false;
 
+  private final DecompilerSettings decompilerSettings = (IS_DECOMPILE_JCAS) ? 
DecompilerSettings.javaDefaults() : null;
+
   public TypeImpl intType;
 
   public TypeImpl stringType;
@@ -1249,6 +1273,57 @@ public class TypeSystemImpl implements T
     // if (this.cas != null) {
     // this.cas.commitTypeSystem();
     // }
+    if (IS_DECOMPILE_JCAS) {  
+      synchronized(GLOBAL_TYPESYS_LOCK) {
+        for(Type t : types) {
+          if (t == null) continue;
+          decompile(t);
+        }
+      }
+    }
+  }
+  
+  private void decompile(Type t) {
+    String name = t.getName();  
+    if (name.endsWith(arrayTypeSuffix)) return;
+    if (decompiled.contains(name)) return;
+    decompiled.add(name);
+    
+    if(JCasImpl.builtInsWithAltNames.contains(name) )
+      name = "org.apache.uima.jcas."+ name.substring(5 /* "uima.".length() */);
+        
+    String fn = "decompiled/" + name + ".java";
+ 
+    try { 
+      final FileOutputStream stream = new FileOutputStream(fn);
+      final BufferedWriter writer = new BufferedWriter(new 
OutputStreamWriter(stream));
+      final PlainTextOutput plainTextOutput = new PlainTextOutput(writer);
+      
+      Decompiler.decompile(
+           name.replace('.', '/'),
+           plainTextOutput,
+           decompilerSettings
+       );
+       writer.close();
+       if (decompiledFailed(fn)) {
+         File f = new File(fn);
+         f.delete();
+       }
+    }
+    catch (final IOException e) {
+      throw new RuntimeException(e);
+    }
+  }
+
+  private boolean decompiledFailed(String fn) throws IOException {
+    BufferedReader rdr = null;
+    try {
+      rdr = new BufferedReader(new FileReader(fn));
+      String line = rdr.readLine();
+      return line != null && line.startsWith("!!! ERROR: Failed to load 
class");
+    } finally {
+      if (null != rdr) rdr.close();
+    }
   }
   
   /**

Modified: 
uima/uimaj/branches/experiment-v3-jcas/uimaj-core/src/main/java/org/apache/uima/jcas/impl/JCasImpl.java
URL: 
http://svn.apache.org/viewvc/uima/uimaj/branches/experiment-v3-jcas/uimaj-core/src/main/java/org/apache/uima/jcas/impl/JCasImpl.java?rev=1691640&r1=1691639&r2=1691640&view=diff
==============================================================================
--- 
uima/uimaj/branches/experiment-v3-jcas/uimaj-core/src/main/java/org/apache/uima/jcas/impl/JCasImpl.java
 (original)
+++ 
uima/uimaj/branches/experiment-v3-jcas/uimaj-core/src/main/java/org/apache/uima/jcas/impl/JCasImpl.java
 Fri Jul 17 21:03:03 2015
@@ -767,7 +767,7 @@ public class JCasImpl extends AbstractCa
     builtInsWithNoJCas.add(CAS.TYPE_NAME_LIST_BASE);
   }
 
-  private static final Collection<String> builtInsWithAltNames = new 
ArrayList<String>();
+  public static final Collection<String> builtInsWithAltNames = new 
ArrayList<String>();
   static { // initialization code
     builtInsWithAltNames.add(CAS.TYPE_NAME_TOP);
     builtInsWithAltNames.add(CAS.TYPE_NAME_STRING_ARRAY);

Added: 
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcas/internal/AnalyzeContent.java
URL: 
http://svn.apache.org/viewvc/uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcas/internal/AnalyzeContent.java?rev=1691640&view=auto
==============================================================================
--- 
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcas/internal/AnalyzeContent.java
 (added)
+++ 
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcas/internal/AnalyzeContent.java
 Fri Jul 17 21:03:03 2015
@@ -0,0 +1,301 @@
+package org.apache.uima.tools.jcas.internal;
+
+import java.util.Arrays;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * Internal class, part of utility to migrate to version 3 of JCas
+ * 
+ * Analyzes one decompiled JCas type to determine if it was customized.
+ * 
+ * If customized, outputs a list of these to standard output.
+ * 
+ */
+
+public class AnalyzeContent {
+
+  private static final boolean trace = false;
+
+  /*********************************************
+   * String fragments reused in patterns below
+   *********************************************/
+  private static final String ppLlAccess = "this\\.jcasType\\.ll_cas\\.ll_";
+  
+  private static final String ppJcasTypeCasted = 
"\\(\\(\\w*_Type\\)this\\.jcasType\\)";
+  
+  private static final String ppFeatOkTst = 
+        "\\s*if \\(\\w*_Type\\.featOkTst \\&\\& " + ppJcasTypeCasted + 
"\\.casFeat_\\w* \\=\\= null\\) \\{"
+      + "\\s*this\\.jcasType\\.jcas\\.throwFeatMissing\\(\"\\w*\", 
\"[\\w\\.]*\"\\);"
+      + "\\s*\\}";
+  
+  private static final String ppFeatCode = ppJcasTypeCasted + 
"\\.casFeatCode_\\w*"; 
+  
+  private static final String ppMaybeValueRef = "(?:, (?:" + ppLlAccess + 
"getFSRef\\(v\\)|v))?";
+
+  /********************************************
+   * instance variables
+   ********************************************/
+
+  final String s;
+  int pos = 0;
+  int savedPos = 0;
+  Matcher m;
+  public String msg;  
+  
+  String packageName;
+  String shortClassName;
+  String shortSuperName;
+  
+  public boolean isCustomized = true;
+
+  private final Brna bPackage = newBrna("package ([^;]*);", "package");
+  private final Brna bImports = newBrna("(\\s*import [^;]*;)+", "imports");
+  private final Brna bClass = newBrna("\\s*public class (\\w*) extends 
(\\w*)\\s*\\{", "class");
+  private final Brna bBp1 = newBrna(
+        "\\s*public static final int typeIndexID;"
+      + "\\s*public static final int type;"
+      + "\\s*static \\{"
+      + "\\s*typeIndexID = JCasRegistry.register\\((\\w*)\\.class\\);"
+      + "\\s*type = (\\w*).typeIndexID;"
+      + "\\s*\\}", "type/index/register");
+  private final Brna bBp2 = newBrna(
+        "\\s*\\@Override"
+      + "\\s*public int getTypeIndexID\\(\\) \\{"
+      + "\\s*return (\\w*)\\.typeIndexID;"
+      + "\\s*\\}"
+      + "\\s*protected (\\w*)\\(\\) \\{"
+      + "\\s*\\}", "getTypeIndex, empty constructor");
+  
+  private final Brna bConstr = newBrna(
+        "\\s*public \\w*\\(final int addr, final TOP_Type type\\) \\{"
+      + "\\s*super\\(addr, type\\);"
+      + "(\\s*this\\.readObject\\(\\);)?"
+      + "\\s*\\}"
+      + "\\s*public \\w*\\(final JCas jcas\\) \\{"
+      + "\\s*super\\(jcas\\);"
+      + "(\\s*this\\.readObject\\(\\);)?" 
+      + "\\s*\\}", "2 constructors");
+      
+  private final Brna bConstrAnnot = newBrna(
+        "\\s*public \\w*\\(final JCas jcas, final int begin, final int end\\) 
\\{"
+      + "\\s*super\\(jcas\\);"
+      + "\\s*this\\.setBegin\\(begin\\);"
+      + "\\s*this\\.setEnd\\(end\\);"
+      + "(\\s*this\\.readObject\\(\\);)?" 
+      + "\\s*\\}", "annot constructor");
+  
+  private final Brna bReadObj = newBrna(
+        "\\s*private void readObject\\(\\) \\{"
+      + "\\s*\\}", "readObject");
+ 
+  private final Brna bSemicolon = newBrna("\\;", "bSemicolon");
+  private final Brna bCloseParen = newBrna("\\)", "bCloseParen");
+  private final Brna bCloseBrace = newBrna("\\s*}", "bCloseBrace");
+  private final Brna bWhiteSpace = newBrna("\\s*", "bWhiteSpace");
+  private final Brna bReturn = newBrna("\\s*return ", "bReturn");
+  private final Brna bEndOfClass = newBrna("\\s*\\}\\s*$", "end of class");
+
+  private final Brna bSimpleCore = newBrna(
+      ppLlAccess + "(?:get|set)\\w*Value\\(this\\.addr, " + ppFeatCode + 
ppMaybeValueRef + "\\)",
+      "SimpleCore");
+
+  private final Brna bArrayCoreStart = newBrna(ppLlAccess + 
"(?:get|set)\\w*ArrayValue\\(", "ArrayCore start");
+  private final Brna bArrayCoreEnd   = newBrna(", i" + ppMaybeValueRef + 
"\\)", "ArrayCore end");
+  private final Brna bArrayCore; // initialized in constructor, otherwise may 
get null value due to order of initialization of fields
+
+  private final Brna bArrayBoundsCheckStart = 
newBrna("\\s*this\\.jcasType\\.jcas\\.checkArrayBounds\\(", "arrayBoundsCheck 
start");
+  private final Brna bArrayBoundsCheckEnd = newBrna(", i\\);", 
"arrayBoundsCheck end");
+  private final Brna bArrayBoundsCheck; // initialized in constructor, 
otherwise may get null value due to order of initialization of fields
+
+  private final Brna bGetFeatureValue; // initialized in constructor, 
otherwise may get null value due to order of initialization of fields
+  private final Brna bSetFeatureValue; // initialized in constructor, 
otherwise may get null value due to order of initialization of fields
+
+  private final Brna pGet1 = newBrna("\\s*public \\w* get\\w*\\(\\) \\{" + 
ppFeatOkTst, "get start");  
+  private final Brna bGet;  // initialized in constructor, otherwise may get 
null value due to order of initialization of fields
+
+  private final Brna bSet1 = newBrna("\\s*public \\w* set\\w*\\(final \\w* 
v\\) \\{" + ppFeatOkTst, "set start");  
+  private final Brna bSet;  // initialized in constructor, otherwise may get 
null value due to order of initialization of fields
+
+  private final Brna bArrayGet1 = newBrna("\\s*public \\w* get\\w*\\(final int 
i\\) \\{" + ppFeatOkTst, "arrayGet start");
+  private final Brna bArrayGet;  // initialized in constructor, otherwise may 
get null value due to order of initialization of fields
+  
+  private final Brna bArraySet1 = newBrna("\\s*public \\w* set\\w*\\(final int 
i, final \\w* v\\) \\{" + ppFeatOkTst, "arraySet start");
+  private final Brna bArraySet;  // initialized in constructor, otherwise may 
get null value due to order of initialization of fields
+
+  private final Brna bCastStart = newBrna("\\s*\\(\\w\\)\\(", "bCastStart");
+  private final Brna bWrapToGetFS_Start = 
newBrna("this\\.jcasType\\.ll_cas\\.ll_getFSForRef\\(", "Wrap_to_get_FS Start");
+
+  /********************************************
+   * functional support for combining matchers
+   ********************************************/
+  @FunctionalInterface
+  private interface Brna { // Boolean Result No Arguments
+    abstract boolean match();
+  }
+
+  private Brna newBrna(String s, String name) {
+    return newBrna(Pattern.compile(s), name);
+  }
+
+  /**
+   * A matcher method object
+   * @param p the pattern to match
+   * @param name for trace output
+   * @return a Brna matcher function
+   */
+  private Brna newBrna(Pattern p, String name) {
+    return () -> {  
+      m.usePattern(p);
+      m.region(pos, s.length());
+      boolean r = m.lookingAt();
+      if (trace) {
+        System.out.format(" *T%s* BrnaName: %s, pattern: %s string: %s%n", r ? 
"+" : "-", name,  p, stringPart());
+      }
+      if (r) {
+        pos = m.end();
+      } 
+      return r;
+    };
+  }
+  
+  private String stringPart() {
+    int endPos = Math.min(s.length(), pos + 120);
+    return s.substring(pos, endPos);
+  }
+
+  /**
+   * A Brna matcher function that is true if all inner matchers return true
+   * @param inners matchers to run, these are run sequentially
+   * @return true if all match. 
+   *              If false the position of the global matcher is reset to its 
original spot 
+   */
+  private Brna all(Brna ... inners) {
+    return () -> { 
+      int savedPos = pos;
+      //debug
+      if (null == inners) {
+        System.out.println("debug");
+      }
+      for (Brna inr : inners) {
+        if (null == inr) {
+          System.out.println("debug");
+        }
+      }
+      if (Arrays.stream(inners).sequential().allMatch(p -> p.match())) {
+        return true;
+      }
+      pos = savedPos;
+      return false;    
+    };
+  }
+  
+  /**
+   * A Brna matcher function that first tries to match with the wrapper, but 
if that fails,
+   * matches the inners without the wrapper
+   * @param head matcher to match first
+   * @param tail matcher to match after the inners
+   * @param inners matchers to match the inner part, with or without the 
wrapper
+   * @return true if matches, with or without the wrapper.  
+   *              If false the position of the global matcher is reset to its 
original spot 
+   */
+  private Brna maybeWrap(String caller, Brna head, Brna tail, Brna ... inners) 
{
+    if (trace) {
+      System.out.println("MaybeWrap: called by " + caller + ", head: " + head);
+    }
+    return () -> {
+      int savedPos = pos;
+      if (head == null) {
+        System.out.println("debug");
+      }
+      if (head.match()) {
+        if (all(inners).match() && tail.match()) {
+          return true;
+        }
+      } else {
+        if (all(inners).match()) {
+          return true;
+        }
+      }
+      pos = savedPos;
+      return false;
+    };
+  }
+
+  /*******************************
+   * Composible matcher functions
+   *******************************/
+  private Brna bMaybeCastResult(Brna innerMatcher) {
+    return maybeWrap("bMaybeCastResult", bCastStart, bCloseParen, 
innerMatcher);
+  }
+  
+  private Brna bMaybeWrapToGetFSResult(Brna core) {
+    return maybeWrap("bMaybeWrapToGetFSResult", bWrapToGetFS_Start, 
bCloseParen,  core);
+  }
+      
+  public AnalyzeContent(String content) {
+    s = content;
+    bArrayCore = all(bArrayCoreStart, bSimpleCore, bArrayCoreEnd);
+
+    bArrayBoundsCheck = all(bArrayBoundsCheckStart, bSimpleCore, 
bArrayBoundsCheckEnd);
+
+    bGetFeatureValue = all(bReturn, 
bMaybeCastResult(bMaybeWrapToGetFSResult(bSimpleCore)), bSemicolon);
+    bSetFeatureValue = all(bWhiteSpace, bSimpleCore, bSemicolon);
+
+    bGet = all(pGet1, bGetFeatureValue, bCloseBrace);
+
+    bSet = all(bSet1, bSetFeatureValue, bCloseBrace);
+
+    bArrayGet = all(bArrayGet1, bArrayBoundsCheck, bReturn, 
bMaybeCastResult(bMaybeWrapToGetFSResult(bArrayCore)), bSemicolon, bCloseBrace);
+    
+    bArraySet = all(bArraySet1, bArrayBoundsCheck, bWhiteSpace, bArrayCore, 
bSemicolon, bCloseBrace);
+    
+    msg = analyzeJCas();
+    
+  }
+  
+  private String analyzeJCas() {    
+   
+    m = Pattern.compile("").matcher(s);
+    if (!bPackage.match()) return "No package statement, string:" + 
stringPart();
+    packageName = m.group(1);
+    
+    if (!bImports.match()) return "Missing imports, string:" + stringPart();
+
+    if (!bClass.match()) return "Missing class, string:" + stringPart();
+    shortClassName = m.group(1);
+    shortSuperName = m.group(2);
+
+    if (!bBp1.match()) return "Missing type/index/register boilerplate, 
string:" + stringPart();
+    if (!m.group(1).equals(shortClassName) ||
+        !m.group(2).equals(shortClassName)) {
+      return String.format("initial boilerplate has wrong name parts: expected 
short class name %s but saw %s and/or %s", 
+          shortClassName, m.group(1), m.group(2));
+    }
+    
+    if (!bBp2.match()) return "missing getTypeIndex and/or empty constructor, 
string:" + stringPart();
+    
+    if (!bConstr.match()) return "missing some constructors, string:" + 
stringPart();
+    
+    bConstrAnnot.match(); // ok if not match
+    
+//    if (!bReadObj.match()) return "readObject missing or customized, 
string:" + stringPart();
+    bReadObj.match();  // ok if not there 
+    /**
+     * match getters and setters
+     */
+    
+    while (!bEndOfClass.match()) {
+      if (!bGet.match()) return "getter customized or moved or missing, 
string:" + stringPart();
+      if (!bSet.match()) return "setter customized or moved or missing, 
string:" + stringPart();
+      
+      if (bArrayGet.match()) {
+        if (!bArraySet.match()) return "array setter customized or moved or 
missing, string:" + stringPart();
+      }
+    }
+    
+    isCustomized = false;
+    return "Not Customized";
+  }
+    
+}

Added: 
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcasgen/DecompiledFilter.java
URL: 
http://svn.apache.org/viewvc/uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcasgen/DecompiledFilter.java?rev=1691640&view=auto
==============================================================================
--- 
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcasgen/DecompiledFilter.java
 (added)
+++ 
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcasgen/DecompiledFilter.java
 Fri Jul 17 21:03:03 2015
@@ -0,0 +1,134 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ * 
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ * 
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.uima.tools.jcasgen;
+
+import java.io.IOException;
+import java.io.UnsupportedEncodingException;
+import java.nio.file.FileSystems;
+import java.nio.file.Files;
+import java.nio.file.Path;
+import java.nio.file.Paths;
+import java.util.HashSet;
+import java.util.Set;
+
+import org.apache.uima.tools.jcas.internal.AnalyzeContent;
+
+public class DecompiledFilter {
+
+  static private Set<String> BUILT_IN_JAVA_NAMES = new HashSet<>();
+  
+  static {
+    for (TypeInfo ti : Jg.builtInTypes.values()) {
+      BUILT_IN_JAVA_NAMES.add(ti.javaNameWithPkg + ".java");
+    }
+  }
+  
+  Path commonDir;
+  Path customizedDir;
+  /**
+   * Processes a directory of decompiled JCasgen files, and produces:
+   *   a listing to system out of the fully qualified names of the 
non-customized files
+   *   a parallel directory xxx-customized holding for all customized files
+   *     a file named xxxCustomize.java
+   *   built-in uima JCas cover classes are ignored.
+   *       
+   * @param args  arg[0] is a relative or absolute path to the decompile 
directory
+   * @throws IOException
+   */
+  public static void main(String[] args) throws IOException {
+    DecompiledFilter df = new DecompiledFilter();
+    df.process(/*args[0]*/"../uimaj-core/decompiled");
+  }
+  
+  private void process(String decompiledFilesStr) throws IOException {
+    Path decompiledFiles = 
FileSystems.getDefault().getPath(decompiledFilesStr);
+    
+    
+    commonDir = decompiledFiles.getParent();
+    customizedDir = Paths.get(commonDir.toString(), 
decompiledFiles.getFileName().toString() + "-customized");
+    
+//    System.out.println("List of all files:");
+//    Files.list(decompiledFiles).forEachOrdered(p -> System.out.println(p));
+    
+    Files.list(decompiledFiles)
+      .filter(p -> !p.toFile().isDirectory())  // skip directories
+      .filter(p -> !isBuiltIn(p))            // skip if builtin
+      .forEach(p -> extractCustomization(p));  
+  }
+  
+  private static boolean isBuiltIn(Path p) {
+    return BUILT_IN_JAVA_NAMES.contains(p.getFileName().toString());
+  }
+  
+  // extract the customization (if any)
+  /**
+   * 
+   * @param p the Path to a decompiled class which may or may not be customized
+   * @return true if the decompiled class is not customized.
+   * @throws IOException 
+   * @throws UnsupportedEncodingException 
+   */
+  private boolean extractCustomization(Path filePath) {
+    String content;
+    try {
+      content = new String(Files.readAllBytes(filePath), "UTF-8");
+    } catch (IOException e) {
+      // TODO Auto-generated catch block
+      e.printStackTrace();
+      return false;
+    }
+    
+    AnalyzeContent m = new AnalyzeContent(content);
+    
+//    try {
+//      if (m.isCustomized) {
+//        if (!customizedDir.toFile().exists()) {
+//          Files.createDirectory(customizedDir);
+//        }
+//        Files.write(Paths.get(customizedDir.toString()), 
m.customizedClass.toString().getBytes("UTF-8"));
+//      }
+//    } catch (IOException e) {
+//      throw new RuntimeException(e);
+//    }
+    
+    
+//    if (m.isSubtypeOfAnnotation()) {
+//      m.verifyCommonConstructorBeginEnd();
+//    }
+//    
+//    m.verifyReadObject();
+//    
+//    if (m.isAtEnd()) return true;
+//    
+//    m.analyzeNextClause();
+//    
+//    if (m.isNextClauseCustomized()) {
+//    
+//    }
+    synchronized (this) {
+      System.out.format("%s %s    %s%n", m.isCustomized ? "Cust   " : 
"notCust" , filePath.toString(), m.isCustomized ? m.msg : "");
+    }
+    return !m.isCustomized;
+  }
+  
+
+
+
+
+}

Modified: 
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcasgen/Jg.java
URL: 
http://svn.apache.org/viewvc/uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcasgen/Jg.java?rev=1691640&r1=1691639&r2=1691640&view=diff
==============================================================================
--- 
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcasgen/Jg.java
 (original)
+++ 
uima/uimaj/branches/experiment-v3-jcas/uimaj-tools/src/main/java/org/apache/uima/tools/jcasgen/Jg.java
 Fri Jul 17 21:03:03 2015
@@ -173,7 +173,7 @@ public class Jg {
   }
 
   // table builtInTypes initialized inside TypeInfo constructor
-  static Map builtInTypes = new HashMap();
+  static Map<String, TypeInfo> builtInTypes = new HashMap<>();
 
   static private void addBuiltInTypeInfo(String casName, String javaName, 
String casElementName) {
     TypeInfo ti = new TypeInfo(casName, javaName, casElementName);
@@ -186,7 +186,7 @@ public class Jg {
 
   // first type needed by fsArrayType; in hash map will be overwritten, though
   static {
-    addBuiltInTypeInfo("uima.cas.TOP", "org.apache.uima.cas.FeatureStructure");
+//    addBuiltInTypeInfo("uima.cas.TOP", 
"org.apache.uima.cas.FeatureStructure"); // overridden below
     addBuiltInTypeInfo("uima.cas.Integer", "int");
     addBuiltInTypeInfo("uima.cas.Float", "float");
     addBuiltInTypeInfo("uima.cas.String", "String");


Reply via email to