changeset 98:7d51140c7453

Merge
author jjg
date Fri, 18 Jun 2010 11:13:26 -0700
parents 8b5712fa8c97 (current diff) 05bf914950a9 (diff)
children 0e4ccb5a0d40 e8cf1a74be06 c28b5920263c
files
diffstat 13 files changed, 443 insertions(+), 110 deletions(-) [+]
line wrap: on
line diff
--- a/.hgtags	Wed Jun 16 17:15:44 2010 -0700
+++ b/.hgtags	Fri Jun 18 11:13:26 2010 -0700
@@ -18,3 +18,4 @@
 78efde88dc5a5a0c1affe42c0e22299d78d7a614 jdk6-b17
 536fbf4fba1f607cbc300ced4c41b71ac75829a1 jdk6-b18
 7306e2127357bcbe9d6b86e2c956aca016d403cd jdk6-b19
+51b6d8d173cd652ac8956879c91782eb36f44741 jdk6-b20
--- a/src/share/classes/com/sun/tools/javac/api/JavacTaskImpl.java	Wed Jun 16 17:15:44 2010 -0700
+++ b/src/share/classes/com/sun/tools/javac/api/JavacTaskImpl.java	Fri Jun 18 11:13:26 2010 -0700
@@ -381,8 +381,8 @@
         return results;
     }
     // where
-        private void handleFlowResults(List<Env<AttrContext>> list, ListBuffer<Element> elems) {
-            for (Env<AttrContext> env: list) {
+        private void handleFlowResults(Queue<Env<AttrContext>> queue, ListBuffer<Element> elems) {
+            for (Env<AttrContext> env: queue) {
                 switch (env.tree.getTag()) {
                     case JCTree.CLASSDEF:
                         JCClassDecl cdef = (JCClassDecl) env.tree;
@@ -396,7 +396,7 @@
                         break;
                 }
             }
-            genList.appendList(list);
+            genList.addAll(queue);
         }
 
 
@@ -424,13 +424,13 @@
             analyze(null);  // ensure all classes have been parsed, entered, and analyzed
 
             if (classes == null) {
-                compiler.generate(compiler.desugar(genList.toList()), results);
+                compiler.generate(compiler.desugar(genList), results);
                 genList.clear();
             }
             else {
                 Filter f = new Filter() {
                         public void process(Env<AttrContext> env) {
-                            compiler.generate(compiler.desugar(List.of(env)), results);
+                            compiler.generate(compiler.desugar(ListBuffer.of(env)), results);
                         }
                     };
                 f.run(genList, classes);
--- a/src/share/classes/com/sun/tools/javac/comp/Enter.java	Wed Jun 16 17:15:44 2010 -0700
+++ b/src/share/classes/com/sun/tools/javac/comp/Enter.java	Fri Jun 18 11:13:26 2010 -0700
@@ -262,8 +262,11 @@
      */
     <T extends JCTree> List<Type> classEnter(List<T> trees, Env<AttrContext> env) {
         ListBuffer<Type> ts = new ListBuffer<Type>();
-        for (List<T> l = trees; l.nonEmpty(); l = l.tail)
-            ts.append(classEnter(l.head, env));
+        for (List<T> l = trees; l.nonEmpty(); l = l.tail) {
+            Type t = classEnter(l.head, env);
+            if (t != null)
+                ts.append(t);
+        }
         return ts.toList();
     }
 
--- a/src/share/classes/com/sun/tools/javac/main/JavaCompiler.java	Wed Jun 16 17:15:44 2010 -0700
+++ b/src/share/classes/com/sun/tools/javac/main/JavaCompiler.java	Fri Jun 18 11:13:26 2010 -0700
@@ -27,6 +27,7 @@
 
 import java.io.*;
 import java.util.HashSet;
+import java.util.LinkedHashSet;
 import java.util.LinkedHashMap;
 import java.util.Map;
 import java.util.MissingResourceException;
@@ -62,6 +63,8 @@
 // TEMP, until we have a more efficient way to save doc comment info
 import com.sun.tools.javac.parser.DocCommentScanner;
 
+import java.util.HashMap;
+import java.util.Queue;
 import javax.lang.model.SourceVersion;
 
 /** This class could be the main entry point for GJC when GJC is used as a
@@ -437,7 +440,25 @@
      */
     public Todo todo;
 
-    private Set<Env<AttrContext>> deferredSugar = new HashSet<Env<AttrContext>>();
+    protected enum CompileState {
+        TODO(0),
+        ATTR(1),
+        FLOW(2);
+        CompileState(int value) {
+            this.value = value;
+        }
+        boolean isDone(CompileState other) {
+            return value >= other.value;
+        }
+        private int value;
+    };
+    protected class CompileStates extends HashMap<Env<AttrContext>,CompileState> {
+        boolean isDone(Env<AttrContext> env, CompileState cs) {
+            CompileState ecs = get(env);
+            return ecs != null && ecs.isDone(cs);
+        }
+    }
+    private CompileStates compileStates = new CompileStates();
 
     /** The set of currently compiled inputfiles, needed to ensure
      *  we don't accidentally overwrite an input file when -s is set.
@@ -454,11 +475,11 @@
             return log.nerrors;
     }
 
-    protected final <T> List<T> stopIfError(ListBuffer<T> listBuffer) {
+    protected final <T> Queue<T> stopIfError(Queue<T> queue) {
         if (errorCount() == 0)
-            return listBuffer.toList();
+            return queue;
         else
-            return List.nil();
+            return ListBuffer.lb();
     }
 
     protected final <T> List<T> stopIfError(List<T> list) {
@@ -764,8 +785,8 @@
                 break;
 
             case BY_FILE:
-                for (List<Env<AttrContext>> list : groupByFile(flow(attribute(todo))).values())
-                    generate(desugar(list));
+                for (Queue<Env<AttrContext>> queue : groupByFile(flow(attribute(todo))).values())
+                    generate(desugar(queue));
                 break;
 
             case BY_TODO:
@@ -782,7 +803,7 @@
         }
 
         if (verbose) {
-            elapsed_msec = elapsed(start_msec);;
+            elapsed_msec = elapsed(start_msec);
             printVerbose("total", Long.toString(elapsed_msec));
         }
 
@@ -1020,11 +1041,11 @@
      * Attribution of the entries in the list does not stop if any errors occur.
      * @returns a list of environments for attributd classes.
      */
-    public List<Env<AttrContext>> attribute(ListBuffer<Env<AttrContext>> envs) {
+    public Queue<Env<AttrContext>> attribute(Queue<Env<AttrContext>> envs) {
         ListBuffer<Env<AttrContext>> results = lb();
-        while (envs.nonEmpty())
-            results.append(attribute(envs.next()));
-        return results.toList();
+        while (!envs.isEmpty())
+            results.append(attribute(envs.remove()));
+        return results;
     }
 
     /**
@@ -1032,6 +1053,9 @@
      * @returns the attributed parse tree
      */
     public Env<AttrContext> attribute(Env<AttrContext> env) {
+        if (compileStates.isDone(env, CompileState.ATTR))
+            return env;
+
         if (verboseCompilePolicy)
             log.printLines(log.noticeWriter, "[attribute " + env.enclClass.sym + "]");
         if (verbose)
@@ -1048,6 +1072,7 @@
                                   env.toplevel.sourcefile);
         try {
             attr.attribClass(env.tree.pos(), env.enclClass.sym);
+            compileStates.put(env, CompileState.ATTR);
         }
         finally {
             log.useSource(prev);
@@ -1062,10 +1087,10 @@
      * If any errors occur, an empty list will be returned.
      * @returns the list of attributed parse trees
      */
-    public List<Env<AttrContext>> flow(List<Env<AttrContext>> envs) {
+    public Queue<Env<AttrContext>> flow(Queue<Env<AttrContext>> envs) {
         ListBuffer<Env<AttrContext>> results = lb();
-        for (List<Env<AttrContext>> l = envs; l.nonEmpty(); l = l.tail) {
-            flow(l.head, results);
+        for (Env<AttrContext> env: envs) {
+            flow(env, results);
         }
         return stopIfError(results);
     }
@@ -1073,7 +1098,7 @@
     /**
      * Perform dataflow checks on an attributed parse tree.
      */
-    public List<Env<AttrContext>> flow(Env<AttrContext> env) {
+    public Queue<Env<AttrContext>> flow(Env<AttrContext> env) {
         ListBuffer<Env<AttrContext>> results = lb();
         flow(env, results);
         return stopIfError(results);
@@ -1087,7 +1112,7 @@
             if (errorCount() > 0)
                 return;
 
-            if (relax || deferredSugar.contains(env)) {
+            if (relax || compileStates.isDone(env, CompileState.FLOW)) {
                 results.append(env);
                 return;
             }
@@ -1102,6 +1127,7 @@
                 make.at(Position.FIRSTPOS);
                 TreeMaker localMake = make.forToplevel(env.toplevel);
                 flow.analyzeTree(env.tree, localMake);
+                compileStates.put(env, CompileState.FLOW);
 
                 if (errorCount() > 0)
                     return;
@@ -1126,10 +1152,10 @@
      * If any errors occur, an empty list will be returned.
      * @returns a list containing the classes to be generated
      */
-    public List<Pair<Env<AttrContext>, JCClassDecl>> desugar(List<Env<AttrContext>> envs) {
+    public Queue<Pair<Env<AttrContext>, JCClassDecl>> desugar(Queue<Env<AttrContext>> envs) {
         ListBuffer<Pair<Env<AttrContext>, JCClassDecl>> results = lb();
-        for (List<Env<AttrContext>> l = envs; l.nonEmpty(); l = l.tail)
-            desugar(l.head, results);
+        for (Env<AttrContext> env: envs)
+            desugar(env, results);
         return stopIfError(results);
     }
 
@@ -1139,7 +1165,7 @@
      * the current implicitSourcePolicy is taken into account.
      * The preparation stops as soon as an error is found.
      */
-    protected void desugar(Env<AttrContext> env, ListBuffer<Pair<Env<AttrContext>, JCClassDecl>> results) {
+    protected void desugar(final Env<AttrContext> env, Queue<Pair<Env<AttrContext>, JCClassDecl>> results) {
         if (errorCount() > 0)
             return;
 
@@ -1148,13 +1174,37 @@
             return;
         }
 
-        if (desugarLater(env)) {
-            if (verboseCompilePolicy)
-                log.printLines(log.noticeWriter, "[defer " + env.enclClass.sym + "]");
-            todo.append(env);
+        /**
+         * As erasure (TransTypes) destroys information needed in flow analysis,
+         * including information in supertypes, we need to ensure that supertypes
+         * are processed through attribute and flow before subtypes are translated.
+         */
+        class ScanNested extends TreeScanner {
+            Set<Env<AttrContext>> dependencies = new LinkedHashSet<Env<AttrContext>>();
+            public void visitClassDef(JCClassDecl node) {
+                Type st = types.supertype(node.sym.type);
+                if (st.tag == TypeTags.CLASS) {
+                    ClassSymbol c = st.tsym.outermostClass();
+                    Env<AttrContext> stEnv = enter.getEnv(c);
+                    if (stEnv != null && env != stEnv) {
+                        if (dependencies.add(stEnv))
+                            scan(stEnv.tree);
+                    }
+                }
+                super.visitClassDef(node);
+            }
+        }
+        ScanNested scanner = new ScanNested();
+        scanner.scan(env.tree);
+        for (Env<AttrContext> dep: scanner.dependencies) {
+            if (!compileStates.isDone(dep, CompileState.FLOW))
+                flow(attribute(dep));
+        }
+
+        //We need to check for error another time as more classes might
+        //have been attributed and analyzed at this stage
+        if (errorCount() > 0)
             return;
-        }
-        deferredSugar.remove(env);
 
         if (verboseCompilePolicy)
             log.printLines(log.noticeWriter, "[desugar " + env.enclClass.sym + "]");
@@ -1174,7 +1224,7 @@
                     List<JCTree> pdef = lower.translateTopLevelClass(env, env.tree, localMake);
                     if (pdef.head != null) {
                         assert pdef.tail.isEmpty();
-                        results.append(new Pair<Env<AttrContext>, JCClassDecl>(env, (JCClassDecl)pdef.head));
+                        results.add(new Pair<Env<AttrContext>, JCClassDecl>(env, (JCClassDecl)pdef.head));
                     }
                 }
                 return;
@@ -1188,7 +1238,7 @@
                     rootClasses.contains((JCClassDecl)untranslated) &&
                     ((cdef.mods.flags & (Flags.PROTECTED|Flags.PUBLIC)) != 0 ||
                      cdef.sym.packge().getQualifiedName() == names.java_lang)) {
-                    results.append(new Pair<Env<AttrContext>, JCClassDecl>(env, removeMethodBodies(cdef)));
+                    results.add(new Pair<Env<AttrContext>, JCClassDecl>(env, removeMethodBodies(cdef)));
                 }
                 return;
             }
@@ -1204,7 +1254,7 @@
                 JCClassDecl cdef = (JCClassDecl)env.tree;
                 if (untranslated instanceof JCClassDecl &&
                     rootClasses.contains((JCClassDecl)untranslated)) {
-                    results.append(new Pair<Env<AttrContext>, JCClassDecl>(env, cdef));
+                    results.add(new Pair<Env<AttrContext>, JCClassDecl>(env, cdef));
                 }
                 return;
             }
@@ -1218,7 +1268,7 @@
             //generate code for each class
             for (List<JCTree> l = cdefs; l.nonEmpty(); l = l.tail) {
                 JCClassDecl cdef = (JCClassDecl)l.head;
-                results.append(new Pair<Env<AttrContext>, JCClassDecl>(env, cdef));
+                results.add(new Pair<Env<AttrContext>, JCClassDecl>(env, cdef));
             }
         }
         finally {
@@ -1227,57 +1277,19 @@
 
     }
 
-    /**
-     * Determine if a class needs to be desugared later.  As erasure
-     * (TransTypes) destroys information needed in flow analysis, we
-     * need to ensure that supertypes are translated before derived
-     * types are translated.
-     */
-    public boolean desugarLater(final Env<AttrContext> env) {
-        if (compilePolicy == CompilePolicy.BY_FILE)
-            return false;
-        if (!devVerbose && deferredSugar.contains(env))
-            // guarantee that compiler terminates
-            return false;
-        class ScanNested extends TreeScanner {
-            Set<Symbol> externalSupers = new HashSet<Symbol>();
-            public void visitClassDef(JCClassDecl node) {
-                Type st = types.supertype(node.sym.type);
-                if (st.tag == TypeTags.CLASS) {
-                    ClassSymbol c = st.tsym.outermostClass();
-                    Env<AttrContext> stEnv = enter.getEnv(c);
-                    if (stEnv != null && env != stEnv)
-                        externalSupers.add(st.tsym);
-                }
-                super.visitClassDef(node);
-            }
-        }
-        ScanNested scanner = new ScanNested();
-        scanner.scan(env.tree);
-        if (scanner.externalSupers.isEmpty())
-            return false;
-        if (!deferredSugar.add(env) && devVerbose) {
-            throw new AssertionError(env.enclClass.sym + " was deferred, " +
-                                     "second time has these external super types " +
-                                     scanner.externalSupers);
-        }
-        return true;
-    }
-
     /** Generates the source or class file for a list of classes.
      * The decision to generate a source file or a class file is
      * based upon the compiler's options.
      * Generation stops if an error occurs while writing files.
      */
-    public void generate(List<Pair<Env<AttrContext>, JCClassDecl>> list) {
-        generate(list, null);
+    public void generate(Queue<Pair<Env<AttrContext>, JCClassDecl>> queue) {
+        generate(queue, null);
     }
 
-    public void generate(List<Pair<Env<AttrContext>, JCClassDecl>> list, ListBuffer<JavaFileObject> results) {
+    public void generate(Queue<Pair<Env<AttrContext>, JCClassDecl>> queue, ListBuffer<JavaFileObject> results) {
         boolean usePrintSource = (stubOutput || sourceOutput || printFlat);
 
-        for (List<Pair<Env<AttrContext>, JCClassDecl>> l = list; l.nonEmpty(); l = l.tail) {
-            Pair<Env<AttrContext>, JCClassDecl> x = l.head;
+        for (Pair<Env<AttrContext>, JCClassDecl> x: queue) {
             Env<AttrContext> env = x.fst;
             JCClassDecl cdef = x.snd;
 
@@ -1319,26 +1331,17 @@
     }
 
         // where
-        Map<JCCompilationUnit, List<Env<AttrContext>>> groupByFile(List<Env<AttrContext>> list) {
+        Map<JCCompilationUnit, Queue<Env<AttrContext>>> groupByFile(Queue<Env<AttrContext>> envs) {
             // use a LinkedHashMap to preserve the order of the original list as much as possible
-            Map<JCCompilationUnit, List<Env<AttrContext>>> map = new LinkedHashMap<JCCompilationUnit, List<Env<AttrContext>>>();
-            Set<JCCompilationUnit> fixupSet = new HashSet<JCTree.JCCompilationUnit>();
-            for (List<Env<AttrContext>> l = list; l.nonEmpty(); l = l.tail) {
-                Env<AttrContext> env = l.head;
-                List<Env<AttrContext>> sublist = map.get(env.toplevel);
-                if (sublist == null)
-                    sublist = List.of(env);
-                else {
-                    // this builds the list for the file in reverse order, so make a note
-                    // to reverse the list before returning.
-                    sublist = sublist.prepend(env);
-                    fixupSet.add(env.toplevel);
+            Map<JCCompilationUnit, Queue<Env<AttrContext>>> map = new LinkedHashMap<JCCompilationUnit, Queue<Env<AttrContext>>>();
+            for (Env<AttrContext> env: envs) {
+                Queue<Env<AttrContext>> sublist = map.get(env.toplevel);
+                if (sublist == null) {
+                    sublist = new ListBuffer<Env<AttrContext>>();
+                    map.put(env.toplevel, sublist);
                 }
-                map.put(env.toplevel, sublist);
+                sublist.add(env);
             }
-            // fixup any lists that need reversing back to the correct order
-            for (JCTree.JCCompilationUnit tree: fixupSet)
-                map.put(tree, map.get(tree).reverse());
             return map;
         }
 
--- a/src/share/classes/com/sun/tools/javac/util/ListBuffer.java	Wed Jun 16 17:15:44 2010 -0700
+++ b/src/share/classes/com/sun/tools/javac/util/ListBuffer.java	Fri Jun 18 11:13:26 2010 -0700
@@ -25,6 +25,7 @@
 
 package com.sun.tools.javac.util;
 
+import java.util.AbstractQueue;
 import java.util.Collection;
 import java.util.Iterator;
 import java.util.NoSuchElementException;
@@ -37,12 +38,18 @@
  *  This code and its internal interfaces are subject to change or
  *  deletion without notice.</b>
  */
-public class ListBuffer<A> implements Collection<A> {
+public class ListBuffer<A> extends AbstractQueue<A> {
 
     public static <T> ListBuffer<T> lb() {
         return new ListBuffer<T>();
     }
 
+    public static <T> ListBuffer<T> of(T x) {
+        ListBuffer<T> lb = new ListBuffer<T>();
+        lb.add(x);
+        return lb;
+    }
+
     /** The list of elements of this buffer.
      */
     public List<A> elems;
@@ -119,6 +126,7 @@
     /** Append an element to buffer.
      */
     public ListBuffer<A> append(A x) {
+        x.getClass(); // null check
         if (shared) copy();
         last.head = x;
         last.setTail(new List<A>(null,null));
@@ -180,20 +188,14 @@
         return elems.head;
     }
 
-    /** Remove the first element in this buffer.
+    /** Return first element in this buffer and remove
      */
-    public void remove() {
+    public A next() {
+        A x = elems.head;
         if (elems != last) {
             elems = elems.tail;
             count--;
         }
-    }
-
-    /** Return first element in this buffer and remove
-     */
-    public A next() {
-        A x = elems.head;
-        remove();
         return x;
     }
 
@@ -219,21 +221,46 @@
     }
 
     public boolean add(A a) {
-        throw new UnsupportedOperationException();
+        append(a);
+        return true;
     }
+
     public boolean remove(Object o) {
         throw new UnsupportedOperationException();
     }
+
     public boolean containsAll(Collection<?> c) {
-        throw new UnsupportedOperationException();
+        for (Object x: c) {
+            if (!contains(x))
+                return false;
+        }
+        return true;
     }
+
     public boolean addAll(Collection<? extends A> c) {
-        throw new UnsupportedOperationException();
+        for (A a: c)
+            append(a);
+        return true;
     }
+
     public boolean removeAll(Collection<?> c) {
         throw new UnsupportedOperationException();
     }
+
     public boolean retainAll(Collection<?> c) {
         throw new UnsupportedOperationException();
     }
+
+    public boolean offer(A a) {
+        append(a);
+        return true;
+    }
+
+    public A poll() {
+        return next();
+    }
+
+    public A peek() {
+        return first();
+    }
 }
--- a/test/tools/javac/6199662/Tree.java	Wed Jun 16 17:15:44 2010 -0700
+++ b/test/tools/javac/6199662/Tree.java	Fri Jun 18 11:13:26 2010 -0700
@@ -23,7 +23,7 @@
 
 /*
  * @test
- * @bug 6199662 6325201
+ * @bug 6199662 6325201 6726015
  * @summary javac: compilation success depends on compilation order
  *
  * @compile Tree.java TreeScanner.java TreeInfo.java
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/tools/javac/6734819/T6734819a.java	Fri Jun 18 11:13:26 2010 -0700
@@ -0,0 +1,39 @@
+/*
+ * Copyright 2008 Sun Microsystems, Inc.  All Rights Reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
+ * CA 95054 USA or visit www.sun.com if you need additional information or
+ * have any questions.
+ */
+
+/*
+ * @test
+ * @bug 6734819
+ * @summary Javac performs flows analysis on already translated classes
+ * @author Maurizio Cimadamore
+ *
+ * @compile/ref=T6734819a.out -XDrawDiagnostics -Xlint:all -XDverboseCompilePolicy T6734819a.java
+ */
+class Y extends W {}
+class W extends Z {}
+
+class Z {
+    void m(Z z) {
+        W w = (W)z;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/tools/javac/6734819/T6734819a.out	Fri Jun 18 11:13:26 2010 -0700
@@ -0,0 +1,12 @@
+[attribute Y]
+[flow Y]
+[attribute W]
+[flow W]
+[attribute Z]
+[flow Z]
+[desugar Y]
+[generate code Y]
+[desugar W]
+[generate code W]
+[desugar Z]
+[generate code Z]
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/tools/javac/6734819/T6734819b.java	Fri Jun 18 11:13:26 2010 -0700
@@ -0,0 +1,35 @@
+/*
+ * Copyright 2008 Sun Microsystems, Inc.  All Rights Reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
+ * CA 95054 USA or visit www.sun.com if you need additional information or
+ * have any questions.
+ */
+
+/*
+ * @test
+ * @bug 6734819
+ * @summary Javac performs flows analysis on already translated classes
+ * @author Maurizio Cimadamore
+ *
+ * @compile/ref=T6734819b.out -XDrawDiagnostics -Xlint:all -XDverboseCompilePolicy T6734819b.java
+ */
+class A extends B {}
+class B {
+    class C extends B {}
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/tools/javac/6734819/T6734819b.out	Fri Jun 18 11:13:26 2010 -0700
@@ -0,0 +1,9 @@
+[attribute A]
+[flow A]
+[attribute B]
+[flow B]
+[desugar A]
+[generate code A]
+[desugar B]
+[generate code B]
+[generate code B]
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/tools/javac/6734819/T6734819c.java	Fri Jun 18 11:13:26 2010 -0700
@@ -0,0 +1,40 @@
+/*
+ * Copyright 2008 Sun Microsystems, Inc.  All Rights Reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
+ * CA 95054 USA or visit www.sun.com if you need additional information or
+ * have any questions.
+ */
+
+/*
+ * @test
+ * @bug 6734819
+ * @summary Javac performs flows analysis on already translated classes
+ * @author Maurizio Cimadamore
+ *
+ * @compile/fail/ref=T6734819c.out -XDrawDiagnostics -Xlint:all -XDverboseCompilePolicy T6734819c.java
+ */
+class Y extends W {}
+class W extends Z {}
+
+class Z {
+    void m(Z z) {
+        return;
+        W w = (W)z;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/tools/javac/6734819/T6734819c.out	Fri Jun 18 11:13:26 2010 -0700
@@ -0,0 +1,8 @@
+[attribute Y]
+[flow Y]
+[attribute W]
+[flow W]
+[attribute Z]
+[flow Z]
+T6734819c.java:38:11: compiler.err.unreachable.stmt
+1 error
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/test/tools/javac/T6956638.java	Fri Jun 18 11:13:26 2010 -0700
@@ -0,0 +1,156 @@
+/*
+ * Copyright (c) 2010, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+import java.io.BufferedWriter;
+import java.io.File;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.io.StringWriter;
+import java.util.Arrays;
+import java.util.Iterator;
+import java.util.List;
+
+import javax.lang.model.element.Element;
+import javax.tools.DiagnosticCollector;
+import javax.tools.JavaCompiler;
+import javax.tools.JavaFileObject;
+import javax.tools.StandardJavaFileManager;
+import javax.tools.ToolProvider;
+
+import com.sun.source.tree.CompilationUnitTree;
+import com.sun.source.util.JavacTask;
+
+/**
+ * @test
+ * @bug 6956638
+ * @summary JavacTask.generate does not generate all required files
+ */
+public class T6956638 {
+    public static void main(String[] args) throws Exception {
+        new T6956638().run();
+    }
+
+    void run() throws Exception {
+        File srcDir = new File("src");
+
+        File[] files = {
+            writeFile(new File(srcDir, "T1.java"),
+                "public class T1 extends T2 {}\n"),
+            writeFile(new File(srcDir, "T2.java"),
+                "public class T2 extends T3 {}\n"),
+            writeFile(new File(srcDir, "T3.java"),
+                "public class T3 { public static final int C = 1; }\n"),
+            writeFile(new File(srcDir, "Test.java"),
+                "public class Test { public static final int D = T1.C; }\n")
+        };
+
+        for (File f1: files) {
+            for (File f2: files) {
+                if (f2 == f1) continue;
+                for (File f3: files) {
+                    if (f3 == f2 || f3 == f1) continue;
+                    for (File f4: files) {
+                        if (f4 == f3 || f4 == f2 || f4 == f1) continue;
+                        try {
+                            test(f1, f2, f3, f4);
+                        } catch (Exception e) {
+                            error(e);
+                        }
+                    }
+                }
+            }
+        }
+
+        if (errors > 0)
+            throw new Exception(errors + " tests failed");
+    }
+
+    void test(File... sourceFiles) throws Exception {
+        System.err.println("Test " + (++count) + ": " + Arrays.asList(sourceFiles));
+
+        File classesDir = new File("classes" + count);
+        classesDir.mkdirs();
+
+        StringWriter compilerOutputStream = new StringWriter();
+
+        List<String> compileOptions = Arrays.asList("-d", classesDir.getPath());
+        JavaCompiler compiler = ToolProvider.getSystemJavaCompiler();
+        DiagnosticCollector<JavaFileObject> diagnosticCollector = new DiagnosticCollector<JavaFileObject>();
+        StandardJavaFileManager fileManager = compiler.getStandardFileManager(diagnosticCollector, null, null);
+        Iterable<? extends JavaFileObject> sourceFileObjects = fileManager.getJavaFileObjects(sourceFiles);
+        System.err.println("1- javac given java source JavaFileObjects " + sourceFileObjects);
+        JavaCompiler.CompilationTask task = compiler.getTask(compilerOutputStream, fileManager, null, compileOptions, null, sourceFileObjects);
+        JavacTask javacTask = (JavacTask) task;
+
+        Iterable<? extends CompilationUnitTree> parsedTrees = javacTask.parse();
+        Iterable<? extends Element> analyzedTrees = javacTask.analyze();
+        Iterable<? extends JavaFileObject> generatedFiles = javacTask.generate();
+
+        System.err.println("2- parsed:" + size(parsedTrees) + " analysed:" + size(analyzedTrees) + " generated:" + size(generatedFiles));
+
+        System.err.print("3-");
+        for (JavaFileObject f : generatedFiles)
+            System.err.print(" " + f);
+        System.err.println("");
+
+        System.err.print("5-");
+        for (File f : classesDir.listFiles())
+            System.err.print(" " + f);
+        System.err.println("");
+
+        System.err.println("----");
+        System.err.println(compilerOutputStream.toString());
+
+        if (size(generatedFiles) != size(parsedTrees)) {
+            throw new Exception("wrong number of files generated: " + size(generatedFiles)
+                    + " expected: " + size(parsedTrees));
+        }
+    }
+
+    private void error(Throwable t) {
+        t.printStackTrace();
+        errors++;
+    }
+
+    int count;
+    int errors;
+
+    private static <E> int size(Iterable<E> x) {
+        int n = 0;
+        for (Iterator<E> iter = x.iterator(); iter.hasNext(); ++n)
+            iter.next();
+        return n;
+    }
+
+    private static File writeFile(File f, String str) throws IOException {
+        f.getParentFile().mkdirs();
+        BufferedWriter fout = new BufferedWriter(new FileWriter(f));
+        try {
+            fout.write(str);
+            fout.flush();
+        } finally {
+            fout.close();
+        }
+        return f;
+    }
+}