Commits

Shashank Bharadwaj committed 9ea78bb

the work in the past few days. I should probably write a decent README of what has happened in this patchset

Comments (0)

Files changed (2)

add-debugging-to-classfile.patch

 # HG changeset patch
-# Parent c542c26d91864708ce3d89502162c8150ae4b860
+# Parent 35b1cf53a286828a65e34c70c7541f95103e3a7c
 
 diff --git a/.externalToolBuilders/ant_expose.launch b/.externalToolBuilders/ant_expose.launch
 --- a/.externalToolBuilders/ant_expose.launch
 diff --git a/src/org/python/compiler/ClassFile.java b/src/org/python/compiler/ClassFile.java
 --- a/src/org/python/compiler/ClassFile.java
 +++ b/src/org/python/compiler/ClassFile.java
-@@ -2,131 +2,174 @@
+@@ -2,131 +2,175 @@
  package org.python.compiler;
  
  import java.io.ByteArrayOutputStream;
 +public class ClassFile {
 +	
 +	private static final boolean DEBUG = false | Options.verbose >= Py.DEBUG;
++	   private static final boolean COMMENT = false | Options.verbose >= Py.COMMENT;
 +	
 +	ClassWriter cw;
 +	ClassVisitor cv;
 +		byte[] ba = cw.toByteArray();
 +		ByteArrayOutputStream baos = new ByteArrayOutputStream(ba.length);
 +		baos.write(ba, 0, ba.length);
-+		if (DEBUG) {
++		if (COMMENT) {
 +			debug(baos);
 +			checkClassVerify(ba);
 +		}
 +		}
 +	}
  }
+diff --git a/src/org/python/compiler/Code.java b/src/org/python/compiler/Code.java
+--- a/src/org/python/compiler/Code.java
++++ b/src/org/python/compiler/Code.java
+@@ -82,9 +82,21 @@
+                 continue;
+             ret.setElementAt(locals[l], l);
+         }
++        System.err.println("Active locals: " + vectorToString(ret));
+         return ret;
+     }
+ 
++    private String vectorToString(Vector<String> ret) {
++        StringBuilder sb = new StringBuilder();
++        sb.append("[");
++        for (String string : ret) {
++            sb.append(string);
++            sb.append(", ");
++        }
++        sb.append("]");
++        return sb.toString();
++    }
++
+     public AnnotationVisitor visitAnnotation(String arg0, boolean arg1) {
+         return mv.visitAnnotation(arg0, arg1);
+     }
 diff --git a/src/org/python/compiler/Module.java b/src/org/python/compiler/Module.java
 --- a/src/org/python/compiler/Module.java
 +++ b/src/org/python/compiler/Module.java

fix-asm-via-cfg.patch

 # HG changeset patch
-# Parent d1983532a776bed79732757dafffe33807c0a3c8
+# Parent ae51dbe75e279fd3480e9e01d8132f120db304a5
 
 diff --git a/.classpath b/.classpath
 --- a/.classpath
 new file mode 100644
 --- /dev/null
 +++ b/src/org/python/antlr/ast/ExceptionRangeStart.java
-@@ -0,0 +1,48 @@
+@@ -0,0 +1,51 @@
 +package org.python.antlr.ast;
 +
 +import java.util.ArrayList;
 +import org.python.antlr.base.stmt;
 +import org.python.compiler.cfg.Edge;
 +
++/**
++ * Node indicating the start of an try-block
++ */
 +public class ExceptionRangeStart extends stmt {
 +
 +    public List<stmt> stmts;
 new file mode 100644
 --- /dev/null
 +++ b/src/org/python/antlr/ast/ExceptionRangeStop.java
-@@ -0,0 +1,48 @@
+@@ -0,0 +1,51 @@
 +package org.python.antlr.ast;
 +
 +import java.util.ArrayList;
 +import org.python.antlr.base.stmt;
 +import org.python.compiler.cfg.Edge;
 +
++/**
++ * Node indicating the end of an try-block
++ */
 +public class ExceptionRangeStop extends stmt {
 +
 +    public List<stmt> stmts;
 new file mode 100644
 --- /dev/null
 +++ b/src/org/python/antlr/ast/FinallyStart.java
-@@ -0,0 +1,29 @@
+@@ -0,0 +1,32 @@
 +package org.python.antlr.ast;
 +
 +import java.util.List;
 +
 +import org.python.antlr.base.stmt;
 +
++/**
++ * Node indicating the start of the finally region in a try-catch-finally block.
++ */
 +public class FinallyStart extends HandlerStart {
 +
 +    public List<stmt> finalBody;
 new file mode 100644
 --- /dev/null
 +++ b/src/org/python/antlr/ast/HandlerStart.java
-@@ -0,0 +1,50 @@
+@@ -0,0 +1,53 @@
 +package org.python.antlr.ast;
 +
 +import java.util.ArrayList;
 +import org.objectweb.asm.Label;
 +import org.python.compiler.cfg.Edge;
 +
++/**
++ * Node indicating the start of a catch handler block.
++ */
 +public class HandlerStart extends ExceptHandler {
 +
 +    public List<Edge> startEdges;
 new file mode 100644
 --- /dev/null
 +++ b/src/org/python/antlr/ast/TryCatchBlock.java
-@@ -0,0 +1,40 @@
+@@ -0,0 +1,43 @@
 +package org.python.antlr.ast;
 +
 +import org.objectweb.asm.Label;
 +import org.python.antlr.base.stmt;
 +
++/**
++ * A node containing the labels for a try-catch block.
++ */
 +public class TryCatchBlock extends stmt {
 +
 +    public Label handler;
 +        return ret;
 +    }
 +
-+    public R visitWithSpecialAssign(WithSpecialAssign node) throws Exception {
++    public R visitWithSpecialLoad(WithSpecialLoad node) throws Exception {
 +        R ret = unhandled_node(node);
 +        traverse(node);
 +        return ret;
 +    public R visitHandlerStart(HandlerStart node) throws Exception;
 +    public R visitFinallyHandlerStart(FinallyStart node) throws Exception;
 +    public R visitTryCatchBlock(TryCatchBlock node) throws Exception;
-+    public R visitWithSpecialAssign(WithSpecialAssign node) throws Exception;
++    public R visitWithSpecialLoad(WithSpecialLoad node) throws Exception;
 +    public R visitWithExit(WithExit node) throws Exception;
  }
 diff --git a/src/org/python/antlr/ast/WithExit.java b/src/org/python/antlr/ast/WithExit.java
 +import org.python.core.PyType;
 +
 +/**
-+ * @author Shashank Bharadwaj
-+ *
++ * A node indicating the __exit__ block of a <code>with</code> statement.
 + */
 +public class WithExit extends stmt {
 +    public static final PyType TYPE = PyType.fromClass(WithExit.class);
-+    
++
 +    public static final int EXIT_IN_EXCEPT = 1;
 +    public static final int EXIT_IN_FINALLY = 2;
-+    
++
 +    public int typeOfAssign;
 +    public expr manager;
 +    public expr exception;
 +
 +    /**
-+     * @param typeOfAssign should be one of EXIT, ENTER or MGR.
-+     * @param manager 
-+     * @param exception 
++     * @param typeOfAssign
++     *            should be one of EXIT, ENTER or MGR.
++     * @param manager
++     * @param exception
 +     */
 +    public WithExit(int typeOfAssign, expr manager, Name exception) {
-+    	this.typeOfAssign = typeOfAssign;
-+    	this.manager = manager;
-+    	this.exception = exception;
-+    }
-+    
++        this.typeOfAssign = typeOfAssign;
++        this.manager = manager;
++        this.exception = exception;
++    }
++
 +    public <R> R accept(VisitorIF<R> visitor) throws Exception {
 +        return visitor.visitWithExit(this);
 +    }
 +        if (manager != null)
 +            manager.accept(visitor);
 +    }
-+    
++
 +    @Override
 +    public String toString() {
 +        return "SpecialAssign(" + typeOfAssign + ")";
 +    }
 +
 +}
-diff --git a/src/org/python/antlr/ast/WithSpecialAssign.java b/src/org/python/antlr/ast/WithSpecialAssign.java
+diff --git a/src/org/python/antlr/ast/WithSpecialLoad.java b/src/org/python/antlr/ast/WithSpecialLoad.java
 new file mode 100644
 --- /dev/null
-+++ b/src/org/python/antlr/ast/WithSpecialAssign.java
++++ b/src/org/python/antlr/ast/WithSpecialLoad.java
 @@ -0,0 +1,47 @@
 +/**
 + * 
 +import org.python.core.PyType;
 +
 +/**
-+ * @author Shashank Bharadwaj
-+ *
++ * Node for the special loads for the <code>with</code> statement.
 + */
-+public class WithSpecialAssign extends expr {
-+    public static final PyType TYPE = PyType.fromClass(WithSpecialAssign.class);
-+    
++public class WithSpecialLoad extends expr {
++    public static final PyType TYPE = PyType.fromClass(WithSpecialLoad.class);
++
 +    public static final int EXIT_IN_EXCEPT = 1;
 +    public static final int ENTER = 2;
 +    public static final int MGR = 3;
-+    
++
 +    public int typeOfAssign;
 +    public expr extraExpr;
 +
 +    /**
-+     * @param typeOfAssign should be one of EXIT, ENTER or MGR.
-+     * @param optionalExpr 
++     * @param typeOfAssign
++     *            should be one of EXIT, ENTER or MGR.
++     * @param optionalExpr
 +     */
-+    public WithSpecialAssign(int typeOfAssign, expr optionalExpr) {
-+    	this.typeOfAssign = typeOfAssign;
-+    	this.extraExpr = optionalExpr;
-+    }
-+    
++    public WithSpecialLoad(int typeOfAssign, expr optionalExpr) {
++        this.typeOfAssign = typeOfAssign;
++        this.extraExpr = optionalExpr;
++    }
++
 +    public <R> R accept(VisitorIF<R> visitor) throws Exception {
-+        return visitor.visitWithSpecialAssign(this);
++        return visitor.visitWithSpecialLoad(this);
 +    }
 +
 +    public void traverse(VisitorIF<?> visitor) throws Exception {
 +        if (extraExpr != null)
 +            extraExpr.accept(visitor);
 +    }
-+    
++
 +    @Override
 +    public String toString() {
 +        return "SpecialAssign(" + typeOfAssign + ")";
  import org.python.antlr.ast.While;
 -import org.python.antlr.ast.With;
 +import org.python.antlr.ast.WithExit;
-+import org.python.antlr.ast.WithSpecialAssign;
++import org.python.antlr.ast.WithSpecialLoad;
  import org.python.antlr.ast.Yield;
  import org.python.antlr.ast.alias;
  import org.python.antlr.ast.cmpopType;
      }
  
      @Override
+@@ -1240,6 +1225,8 @@
+         code.ifnonnull(start_loop);
+ 
+         finishLoop(savebcf);
++        code.freeLocal(iter_tmp);
++        code.freeLocal(expr_tmp);
+ 
+         if (node.getInternalOrelse() != null) {
+             //Do else clause if provided
+@@ -1248,8 +1235,6 @@
+ 
+         code.label(break_loop);
+ 
+-        code.freeLocal(iter_tmp);
+-        code.freeLocal(expr_tmp);
+ 
+         // Probably need to detect "guaranteed exits"
+         return null;
 @@ -1258,7 +1243,11 @@
      public void exceptionTest(int exc, Label end_of_exceptions,
              TryExcept node, int index)
              }
  
              //do exception body
-@@ -1294,127 +1288,88 @@
+@@ -1294,41 +1288,29 @@
      }
  
      @Override
 -        Object ret;
 -
 -        ExceptionHandler inFinally = new ExceptionHandler(node);
-+    	TryExcept finallyExpr = (TryExcept) node.getInternalFinalbody().remove(0);
-+    	FinallyStart handlerBlock  = (FinallyStart) finallyExpr.getInternalHandlers().get(0);
-+    	Label handler_start = handlerBlock.start;
-+    	Label handler_end = handlerBlock.end;
-+    	Label finally_body_label = new Label();
++        TryExcept finallyExpr = (TryExcept) node.getInternalFinalbody().remove(0);
++        FinallyStart handlerBlock = (FinallyStart) finallyExpr.getInternalHandlers().get(0);
++        Label handler_start = handlerBlock.start;
++        Label handler_end = handlerBlock.end;
  
          // Do protected suite
 -        exceptionHandlers.push(inFinally);
          code.astore(excLocal);
  
          code.aload(excLocal);
-         loadFrame();
- 
--        code.invokestatic(p(Py.class), "addTraceback",
--                sig(Void.TYPE, Throwable.class, PyFrame.class));
-+        code.invokestatic(p(Py.class), "addTraceback", sig(Void.TYPE, Throwable.class, PyFrame.class));
+@@ -1337,109 +1319,77 @@
+         code.invokestatic(p(Py.class), "addTraceback",
+                 sig(Void.TYPE, Throwable.class, PyFrame.class));
  
 -        inlineFinally(inFinally);
-+        // Do finally body
-+        code.label(finally_body_label);
-+        suite(node.getInternalFinalbody());
-+
          code.aload(excLocal);
          code.checkcast(p(Throwable.class));
          code.athrow();
 -        }
 +    @Override
 +    public Object visitExceptionRangeStart(ExceptionRangeStart node) throws Exception {
-+    	code.label(node.start);
-+    	return null;
++        code.label(node.start);
++        return null;
      }
  
 -    private void reenterProtectedBody(ExceptionHandler handler) throws Exception {
 -        handler.exceptionStarts.addElement(restart);
 +    @Override
 +    public Object visitExceptionRangeStop(ExceptionRangeStop node) throws Exception {
-+    	code.label(node.end);
-+    	return null;
++        code.label(node.end);
++        return null;
      }
  
 -    /**
 -        }
 +    @Override
 +    public Object visitHandlerStart(HandlerStart node) throws Exception {
-+    	// XXX:: visit the nodes' label or is there nothing to do?
-+    	return null;
++        // XXX:: visit the nodes' label or is there nothing to do?
++        return null;
 +    }
 +
 +    @Override
 +    public Object visitFinallyHandlerStart(FinallyStart node) throws Exception {
-+    	return super.visitHandlerStart(node);
++        return super.visitHandlerStart(node);
      }
  
      @Override
 -        Label handler_start = new Label();
 -        Label handler_end = new Label();
 -        ExceptionHandler handler = new ExceptionHandler();
-+    	HandlerStart handlerBlock = (HandlerStart) node.getInternalHandlers().get(0);
-+    	Label handler_start = handlerBlock.start;
-+    	Label handler_end = handlerBlock.end;
++        HandlerStart handlerBlock = (HandlerStart) node.getInternalHandlers().get(0);
++        Label handler_start = handlerBlock.start;
++        Label handler_end = handlerBlock.end;
  
 -        code.label(start);
 -        handler.exceptionStarts.addElement(start);
 -        exceptionHandlers.push(handler);
-         //Do suite
+-        //Do suite
++        // Do suite
          Object exit = suite(node.getInternalBody());
 -        exceptionHandlers.pop();
 -        code.label(end);
 -
          loadFrame();
  
-         code.invokestatic(p(Py.class), "setException", sig(PyException.class, Throwable.class,
-@@ -1439,7 +1394,6 @@
+-        code.invokestatic(p(Py.class), "setException", sig(PyException.class, Throwable.class,
+-                PyFrame.class));
++        code.invokestatic(p(Py.class), "setException",
++                sig(PyException.class, Throwable.class, PyFrame.class));
+ 
+         int exc = code.getFinallyLocal(p(Throwable.class));
+         code.astore(exc);
+ 
+         if (node.getInternalOrelse() == null) {
+-            //No else clause to worry about
++            // No else clause to worry about
+             exceptionTest(exc, handler_end, node, 1);
+             code.label(handler_end);
+         } else {
+-            //Have else clause
++            // Have else clause
+             Label else_end = new Label();
+             exceptionTest(exc, else_end, node, 1);
+             code.label(handler_end);
+ 
+-            //do else clause
++            // do else clause
+             suite(node.getInternalOrelse());
+             code.label(else_end);
          }
  
          code.freeFinallyLocal(exc);
          return null;
      }
  
-@@ -1449,13 +1403,14 @@
+@@ -1449,13 +1399,14 @@
      }
  
      public Object suite(java.util.List<stmt> stmts) throws Exception {
      }
  
      @Override
-@@ -2263,7 +2218,7 @@
+@@ -2263,7 +2214,7 @@
              super(tree, value);
          }
      }
      @Override
      public Object visitLambda(Lambda node) throws Exception {
          String name = "<lambda>";
-@@ -2614,125 +2569,63 @@
+@@ -2614,125 +2565,63 @@
      }
  
      @Override
 +    }
 +    
 +    @Override
-+    public Object visitWithSpecialAssign(WithSpecialAssign node) throws Exception {
++    public Object visitWithSpecialLoad(WithSpecialLoad node) throws Exception {
          final Method contextGuard_getManager = Method.getMethod(
                  "org.python.core.ContextManager getManager (org.python.core.PyObject)");
          final Method __enter__ = Method.getMethod(
 -        if (node.getInternalOptional_vars() != null) {
 -            set(node.getInternalOptional_vars(), value_tmp);
 +        switch (node.typeOfAssign) {
-+        case WithSpecialAssign.ENTER:
++        case WithSpecialLoad.ENTER:
 +            visit(node.extraExpr);
 +            loadThreadState();
 +            code.invokeinterface(Type.getType(ContextManager.class).getInternalName(),
 +                    __enter__.getName(), __enter__.getDescriptor());
 +            break;
-+        case WithSpecialAssign.MGR:
++        case WithSpecialLoad.MGR:
 +            visit(node.extraExpr);
 +            code.invokestatic(Type.getType(ContextGuard.class).getInternalName(),
 +                    contextGuard_getManager.getName(), contextGuard_getManager.getDescriptor());
          return null;
      }
  
-@@ -2741,62 +2634,4 @@
+@@ -2741,62 +2630,4 @@
          throw new Exception("Unhandled node " + node);
      }
  
 new file mode 100644
 --- /dev/null
 +++ b/src/org/python/compiler/JDK7Compiler.java
-@@ -0,0 +1,39 @@
+@@ -0,0 +1,38 @@
 +package org.python.compiler;
 +
 +import org.python.antlr.ast.TryCatchBlock;
 + * {@link TryCatchBlock} nodes into the IR. Then the {@link
 + * LegacyCompiler#compile(...)} is called to do the actual byte-code generation.
 + * 
-+ * @author Shashank Bharadwaj
 + */
 +public class JDK7Compiler extends LegacyCompiler {
 +
 +    @Override
 +    public PythonCodeBundle compile(mod node, String name, String filename, boolean linenumbers,
 +            boolean printResults, CompilerFlags cflags) throws Exception {
-+        Py.writeDebug(TAG, "Initial tree\n"  + IRPrinter.print(node) );
++        Py.writeDebug(TAG, "Initial tree\n" + IRPrinter.print(node));
 +        node = (mod) new IRBuilder().visit(node);
 +        Py.writeDebug(TAG, "Successfully built the IR\n" + IRPrinter.print(node));
 +        node = (mod) new StampTryCatch().visit(node);
-+        Py.writeDebug(TAG, "Tree after fully built\n" /* + IRPrinter.print(node) */);
++        Py.writeDebug(TAG, "Tree after fully built\n" + IRPrinter.print(node));
 +        return super.compile(node, name, filename, linenumbers, printResults, cflags);
 +    }
 +
 new file mode 100644
 --- /dev/null
 +++ b/src/org/python/compiler/cfg/IRBuilder.java
-@@ -0,0 +1,376 @@
+@@ -0,0 +1,367 @@
 +package org.python.compiler.cfg;
 +
 +import java.util.ArrayList;
 +import org.python.antlr.ast.While;
 +import org.python.antlr.ast.With;
 +import org.python.antlr.ast.WithExit;
-+import org.python.antlr.ast.WithSpecialAssign;
++import org.python.antlr.ast.WithSpecialLoad;
 +import org.python.antlr.ast.expr_contextType;
 +import org.python.antlr.base.excepthandler;
 +import org.python.antlr.base.expr;
 + * 
 + * This visitor runs through the AST to build a IR. The IR is very similar to
 + * the AST for most nodes, except for {@link TryExcept} and {@link TryFinally}.
-+ * 
-+ * @author Shashank Bharadwaj
 + */
 +public class IRBuilder extends ScopedVisitor {
 +
 +        List<stmt> body = suite(node.getInternalBody(), finally_handler);
 +        body.addAll(suited_finally);
 +
-+        suited_finally.add(0, new TryExcept(node, null,
-+                Collections.singletonList((excepthandler) finally_handler), null));
++        suited_finally.add(
++                0,
++                new TryExcept(node, null, Collections
++                        .singletonList((excepthandler) finally_handler), null));
 +
 +        TryFinally new_node = new TryFinally(node.getToken(), body, suited_finally);
 +        return new_node;
 +        doFinallysDownTo(0);
 +        return node;
 +    }
-+    
-+    private Name genLoadName(Token token, String name){
++
++    private Name genLoadName(Token token, String name) {
 +        return new Name(token, name, expr_contextType.Load);
 +    }
 +
 +        expr VAR = node.getInternalOptional_vars();
 +        List<stmt> BLOCK = node.getInternalBody();
 +        List<stmt> outer_try_body = new ArrayList<stmt>();
-+        
++
 +        // mgr = (EXPR)
 +        data.stmts.add(new Assign(token, Collections.singletonList((expr) new Name(token, mgr,
-+                expr_contextType.Store)), new WithSpecialAssign(WithSpecialAssign.MGR, EXPR)));
++                expr_contextType.Store)), new WithSpecialLoad(WithSpecialLoad.MGR, EXPR)));
 +
 +        // value = type(mgr).__enter__(mgr)
 +        data.stmts.add(new Assign(token, Collections.singletonList((expr) new Name(token, value,
-+                expr_contextType.Store)), new WithSpecialAssign(WithSpecialAssign.ENTER, loadMgr)));
++                expr_contextType.Store)), new WithSpecialLoad(WithSpecialLoad.ENTER, loadMgr)));
 +
 +        // exc = True
 +        data.stmts.add(new Assign(token, Collections.singletonList((expr) new Name(token, exc,
 +                expr_contextType.Store)), genLoadName(token, "True")));
-+        /* 
-+         * try:
-+         *   try:
-+         *     VAR = value  # Only if "as VAR" is present
-+         *     BLOCK
-+         *   except:
-+         *     # The exceptional case is handled here
-+         *     exc = False
-+         *     if not exit(mgr, *sys.exc_info()):
-+         *       raise
-+         *   # The exception is swallowed if exit() returns true
-+         *   finally:
-+         *     # The normal and non-local-goto cases are handled here
-+         *     if exc:
-+         *       exit(mgr, None, None, None)
++        /*
++         * try: try: VAR = value # Only if "as VAR" is present BLOCK except: #
++         * The exceptional case is handled here exc = False if not exit(mgr,
++         * *sys.exc_info()): raise # The exception is swallowed if exit()
++         * returns true finally: # The normal and non-local-goto cases are
++         * handled here if exc: exit(mgr, None, None, None)
 +         */
 +        List<stmt> handler_body = new ArrayList<stmt>();
 +        handler_body.add(new Assign(token, Collections.singletonList((expr) new Name(token, exc,
 +                .singletonList((excepthandler) new ExceptHandler(token, null, new Name(token,
 +                        excObject, expr_contextType.Store), handler_body)), null));
 +        List<stmt> finallyBody = new ArrayList<stmt>();
-+        finallyBody.add(new If(token, genLoadName(token, exc), 
-+                Collections.singletonList(loadExitInFinally), Collections.<stmt> emptyList()));
++        finallyBody.add(new If(token, genLoadName(token, exc), Collections
++                .singletonList(loadExitInFinally), Collections.<stmt> emptyList()));
 +        TryFinally try_finally = new TryFinally(token, outer_try_body, finallyBody);
 +        return visit(try_finally);
 +    }
 new file mode 100644
 --- /dev/null
 +++ b/src/org/python/compiler/cfg/IRPrinter.java
-@@ -0,0 +1,79 @@
+@@ -0,0 +1,76 @@
 +package org.python.compiler.cfg;
 +
 +import java.util.ArrayList;
 +
 +/**
 + * A dirty pretty-printer. This code below tries to
-+ * 
-+ * @author Shashank Bharadwaj
-+ * 
 + */
 +public class IRPrinter extends Visitor {
 +
 new file mode 100644
 --- /dev/null
 +++ b/src/org/python/compiler/cfg/StampTryCatch.java
-@@ -0,0 +1,65 @@
+@@ -0,0 +1,69 @@
 +package org.python.compiler.cfg;
 +
 +import static org.python.util.CodegenUtils.p;
 +import org.python.antlr.ast.TryFinally;
 +import org.python.antlr.base.stmt;
 +
++/**
++ * For all TryExcept and TryFinally nodes, insert the {@link TryCatchBlock} at
++ * the start of the enclosing scope.
++ */
 +public class StampTryCatch extends ScopedVisitor {
 +
 +    List<stmt> additions;
 new file mode 100644
 --- /dev/null
 +++ b/src/org/python/compiler/cfg/TransitiveVisitor.java
-@@ -0,0 +1,638 @@
+@@ -0,0 +1,640 @@
 +package org.python.compiler.cfg;
 +
 +import java.util.ArrayList;
 +import org.python.antlr.ast.While;
 +import org.python.antlr.ast.With;
 +import org.python.antlr.ast.WithExit;
-+import org.python.antlr.ast.WithSpecialAssign;
++import org.python.antlr.ast.WithSpecialLoad;
 +import org.python.antlr.ast.Yield;
 +import org.python.antlr.ast.arguments;
 +import org.python.antlr.ast.comprehension;
 +import org.python.antlr.base.slice;
 +import org.python.antlr.base.stmt;
 +
++/**
++ * A visitor which creates new AST from the given one.
++ */
 +public class TransitiveVisitor extends Visitor {
 +
 +    public TransitiveVisitor() {
 +        expr msg = (expr) visitNotNull(node.getInternalMsg());
 +        expr test = (expr) visitNotNull(node.getInternalTest());
 +        Assert new_node = new Assert(node.getToken(), test, msg);
-+
 +        return new_node;
 +    }
 +
 +
 +        return new_node;
 +    }
-+    
++
 +    @Override
-+    public Object visitWithSpecialAssign(WithSpecialAssign node) throws Exception {
++    public Object visitWithSpecialLoad(WithSpecialLoad node) throws Exception {
 +        return node;
 +    }
 +
 +    public Object visitWithExit(WithExit node) throws Exception {
 +        return node;
 +    }
-+    
++
 +    @Override
 +    public Object visitRaise(Raise node) throws Exception {
 +        expr inst = visitNotNull(node.getInternalInst());
      private static PythonCompiler loadDefaultCompiler() {
 -        return new LegacyCompiler();
 +        // make the JDK7 compiler the default.
-+    	return new JDK7Compiler();
++        return new JDK7Compiler();
      }
  
      public static PyCode compile(mod node, String name, String filename,
  
      private final PyObject __enter__method;
      private final PyObject __exit__method;
-diff --git a/src/org/python/core/ContextManager.java b/src/org/python/core/ContextManager.java
---- a/src/org/python/core/ContextManager.java
-+++ b/src/org/python/core/ContextManager.java
-@@ -1,11 +1,14 @@
- package org.python.core;
- 
--/** A <code>PyObject</code> that provides <code>__enter__</code> and <code>__exit__</code> methods for use in the with-statement.
-- *
-+/**
-+ * A <code>PyObject</code> that provides <code>__enter__</code> and
-+ * <code>__exit__</code> methods for use in the with-statement.
-+ * 
-  * Implementing context managers can then be potentially inlined by the JVM.
-  */
- 
- public interface ContextManager {
--    public PyObject __enter__(ThreadState ts);
--    public boolean __exit__(ThreadState ts, PyException exception);
-+	public PyObject __enter__(ThreadState ts);
-+
-+	public boolean __exit__(ThreadState ts, PyException exception);
- }
-diff --git a/src/org/python/core/Py.java b/src/org/python/core/Py.java
---- a/src/org/python/core/Py.java
-+++ b/src/org/python/core/Py.java
-@@ -25,6 +25,8 @@
- import com.kenai.constantine.platform.Errno;
- import java.util.ArrayList;
- import java.util.List;
-+
-+import org.python.compiler.CodeCompiler;
- import org.python.core.adapter.ClassicPyObjectAdapter;
- import org.python.core.adapter.ExtensiblePyObjectAdapter;
- import org.python.modules.posix.PosixModule;
-@@ -119,7 +121,7 @@
-         PyObject args = new PyTuple(Py.newInteger(value), PosixModule.strerror(value));
-         return new PyException(Py.OSError, args);
-     }
--    
-+
-     public static PyException OSError(Constant errno, PyObject filename) {
-         int value = errno.value();
-         // Pass to strerror because constantine currently lacks Errno descriptions on
-@@ -420,7 +422,7 @@
-     public static void UnicodeWarning(String message) {
-         warning(UnicodeWarning, message);
-     }
--    
-+
-     public static PyObject BytesWarning;
-     public static void BytesWarning(String message) {
-         warning(BytesWarning, message);
-@@ -620,7 +622,7 @@
-         }
-         return new PyStringMap();
-     }
--    
-+
-     public static PyUnicode newUnicode(char c) {
-         return (PyUnicode) makeCharacter(c, true);
-     }
-@@ -846,36 +848,36 @@
-         		          " in sys.classLoader");
-         	}
-             return loadAndInitClass(name, classLoader);
--        } 
-+        }
-         if (!syspathJavaLoaderRestricted) {
-             try {
-                 classLoader = imp.getSyspathJavaLoader();
-                 if (classLoader != null && reason != null) {
- 	                writeDebug("import", "trying " + name + " as " + reason +
- 	                        " in SysPathJavaLoader");
--                }                
-+                }
-             } catch (SecurityException e) {
-                 syspathJavaLoaderRestricted = true;
-             }
--        }        
-+        }
-         if (syspathJavaLoaderRestricted) {
-         	classLoader = imp.getParentClassLoader();
-             if (classLoader != null && reason != null) {
-                 writeDebug("import", "trying " + name + " as " + reason +
--                        " in Jython's parent class loader");     
-+                        " in Jython's parent class loader");
-             }
--        } 
-+        }
-         if (classLoader != null) {
-             try {
-             	return loadAndInitClass(name, classLoader);
-             } catch (ClassNotFoundException cnfe) {
-                 // let the default classloader try
-             	// XXX: by trying another classloader that may not be on a
--            	//      parent/child relationship with the Jython's parent 
-+            	//      parent/child relationship with the Jython's parent
-             	//      classsloader we are risking some nasty class loading
--            	//      problems (such as having two incompatible copies for 
--            	//      the same class that is itself a dependency of two 
--            	//      classes loaded from these two different class loaders) 
-+            	//      problems (such as having two incompatible copies for
-+            	//      the same class that is itself a dependency of two
-+            	//      classes loaded from these two different class loaders)
-             }
-         }
-         if (reason != null) {
-@@ -884,7 +886,7 @@
-         }
-         return loadAndInitClass(name, Thread.currentThread().getContextClassLoader());
-     }
--    
-+
-     /**
-      * Tries to find a Java class.
-      * @param name Name of the Java class.
-@@ -906,18 +908,18 @@
-     }
- 
-     /**
--     * Tries to find a Java class. 
--     * 
--     * Unless {@link #findClass(String)}, it raises a JavaError 
-+     * Tries to find a Java class.
-+     *
-+     * Unless {@link #findClass(String)}, it raises a JavaError
-      * if the class was found but there were problems loading it.
-      * @param name Name of the Java class.
-      * @param reason Reason for finding the class. Used for debugging messages.
-      * @return The class, or null if it wasn't found
--     * @throws JavaError wrapping LinkageErrors/IllegalArgumentExceptions 
-+     * @throws JavaError wrapping LinkageErrors/IllegalArgumentExceptions
-      * occurred when the class is found but can't be loaded.
-      */
-     public static Class<?> findClassEx(String name, String reason) {
--        try {            
-+        try {
-             return findClassInternal(name, reason);
-         } catch (ClassNotFoundException e) {
-             return null;
-@@ -929,13 +931,13 @@
-     }
- 
-     // An alias to express intent (since boolean flags aren't exactly obvious).
--    // We *need* to initialize classes on findClass/findClassEx, so that import 
-+    // We *need* to initialize classes on findClass/findClassEx, so that import
-     // statements can trigger static initializers
-     private static Class<?> loadAndInitClass(String name, ClassLoader loader) throws ClassNotFoundException {
-     	return Class.forName(name, true, loader);
--    } 
-- 
--    
-+    }
-+
-+
-     public static void initProxy(PyProxy proxy, String module, String pyclass, Object[] args)
-     {
-         if (proxy._getPyInstance() != null)
-@@ -1963,7 +1965,7 @@
-             }
-             return false;
-         }
--        
-+
-         checkClass(cls, "isinstance() arg 2 must be a class, type, or tuple of classes and types");
-         PyObject instCls = inst.__findattr__("__class__");
-         if (instCls == null) {
 diff --git a/src/org/python/core/imp.java b/src/org/python/core/imp.java
 --- a/src/org/python/core/imp.java
 +++ b/src/org/python/core/imp.java
 new file mode 100644
 --- /dev/null
 +++ b/tmp/test.py
-@@ -0,0 +1,11 @@
+@@ -0,0 +1,9 @@
 +def foo():
-+    for test in []:
-+        yield test
-+    else:
++    for i in [1]:
 +        try:
 +            yield 1
 +        except Exception, e: