stephan 2004/06/03 07:30:39
Modified: src/blocks/javaflow/java/org/apache/cocoon/components/flow/java
ContinuationClassLoader.java
src/blocks/javaflow/test/org/apache/cocoon/components/flow/java/test
SimpleFlow.java
Log:
Fixing problem of null object in local variables.
Create null constants instead of storing them into the continuation.
Revision Changes Path
1.8 +65 -7
cocoon-2.1/src/blocks/javaflow/java/org/apache/cocoon/components/flow/java/ContinuationClassLoader.java
Index: ContinuationClassLoader.java
===================================================================
RCS file:
/home/cvs/cocoon-2.1/src/blocks/javaflow/java/org/apache/cocoon/components/flow/java/ContinuationClassLoader.java,v
retrieving revision 1.7
retrieving revision 1.8
diff -u -r1.7 -r1.8
--- ContinuationClassLoader.java 3 Jun 2004 12:43:27 -0000 1.7
+++ ContinuationClassLoader.java 3 Jun 2004 14:30:39 -0000 1.8
@@ -143,13 +143,41 @@
// analyse the code of the method to create the frame
// information about every instruction
ControlFlowGraph cfg = new ControlFlowGraph(method);
+
+ //System.out.println("analyse " + methods[i].getName());
analyse(clazz, method, cfg, ev);
- // add intercepting code
+
+ // add intercepting code
+ //System.out.println("rewriting " + methods[i].getName());
rewrite(method, cfg);
+
+ // make last optional check for consistency
+ /*System.out.println("check " + methods[i].getName());
+
+ try {
+ cfg = new ControlFlowGraph(method);
+ analyse(clazz, method, cfg, ev);
+ printFrameInfo(method, cfg);
+ } catch (Exception e) {
+ e.printStackTrace();
+ throw new ClassNotFoundException("Rewritten method is
not consistent", e);
+ }*/
+
// make last optional check for consistency
clazz.replaceMethod(methods[i], method.getMethod());
}
}
+
+ /*byte[] changed = clazz.getJavaClass().getBytes();
+ try {
+ java.io.FileOutputStream out = new
java.io.FileOutputStream(clazz.getClassName() + ".rewritten.class");
+ out.write(changed);
+ out.flush();
+ out.close();
+ } catch (java.io.IOException ioe) {
+ ioe.printStackTrace();
+ }*/
+
clazz.addInterface(CONTINUATIONCAPABLE_CLASS);
return clazz.getJavaClass().getBytes();
}
@@ -259,6 +287,36 @@
}
}
}
+
+ private void printFrameInfo(MethodGen method, ControlFlowGraph cfg) {
+ InstructionHandle handle = method.getInstructionList().getStart();
+ do {
+ System.out.println(handle);
+ try {
+ InstructionContext context = cfg.contextOf(handle);
+
+ Frame f = context.getOutFrame(new ArrayList());
+
+ LocalVariables lvs = f.getLocals();
+ System.out.print("Locales: ");
+ for (int i = 0; i < lvs.maxLocals(); i++) {
+ System.out.print(lvs.get(i) + ",");
+ }
+ System.out.println();
+
+ OperandStack os = f.getStack();
+ System.out.print(" Stack: ");
+ for (int i = 0; i < os.size(); i++) {
+ System.out.print(os.peek(i) + ",");
+ }
+ System.out.println();
+ }
+ catch (AssertionViolatedException ave) {
+ System.out.println("no frame information");
+ }
+ }
+ while ((handle = handle.getNext()) != null);
+ }
private void rewrite(MethodGen method, ControlFlowGraph cfg)
throws ClassNotFoundException {
@@ -483,7 +541,7 @@
insList.append(InstructionFactory.createLoad(STACK_TYPE,
method.getMaxLocals()+1));
insList.append(new SWAP()); // TODO: check for types with
two words on stack
insList.append(insFactory.createInvoke(STACK_CLASS,
getPushMethod(type), Type.VOID, new Type[]{type}, Constants.INVOKEVIRTUAL));
- } else if (type == null) {
+ } else if (type.equals(Type.NULL)) {
insList.append(InstructionConstants.POP);
} else if (type instanceof UninitializedObjectType) {
// After the remove of new, there shouldn't be a
@@ -512,7 +570,7 @@
if (type.getSize() < 2 && !type.equals(Type.FLOAT))
type = Type.INT;
insList.append(insFactory.createInvoke(STACK_CLASS,
getPushMethod(type), Type.VOID, new Type[]{type}, Constants.INVOKEVIRTUAL));
- } else if (type == null) {
+ } else if (type.equals(Type.NULL)) {
// no need to save null
} else if (type instanceof UninitializedObjectType) {
// no need to save uninitialized objects
@@ -552,7 +610,7 @@
}
insList.append(insFactory.createInvoke(STACK_CLASS,
getPopMethod(type), type, Type.NO_ARGS, Constants.INVOKEVIRTUAL));
insList.append(InstructionFactory.createStore(type, i));
- } else if (type == null) {
+ } else if (type.equals(Type.NULL)) {
insList.append(new ACONST_NULL());
insList.append(InstructionFactory.createStore(new
ObjectType("<null object>"), i));
} else if (type instanceof UninitializedObjectType) {
@@ -561,7 +619,7 @@
} else if (type instanceof ReferenceType) {
insList.append(InstructionFactory.createLoad(STACK_TYPE,
method.getMaxLocals()+1));
insList.append(insFactory.createInvoke(STACK_CLASS,
getPopMethod(Type.OBJECT), Type.OBJECT, Type.NO_ARGS, Constants.INVOKEVIRTUAL));
- if (!type.equals(Type.OBJECT) && (!type.equals(Type.NULL))) {
+ if (!type.equals(Type.OBJECT)) {
insList.append(insFactory.createCast(Type.OBJECT, type));
}
insList.append(InstructionFactory.createStore(type, i));
@@ -582,7 +640,7 @@
}
insList.append(InstructionFactory.createLoad(STACK_TYPE,
method.getMaxLocals()+1));
insList.append(insFactory.createInvoke(STACK_CLASS,
getPopMethod(type), type, Type.NO_ARGS, Constants.INVOKEVIRTUAL));
- } else if (type == null) {
+ } else if (type.equals(Type.NULL)) {
insList.append(new ACONST_NULL());
} else if (type instanceof UninitializedObjectType) {
// After the remove of new, there shouldn't be a
1.4 +24 -2
cocoon-2.1/src/blocks/javaflow/test/org/apache/cocoon/components/flow/java/test/SimpleFlow.java
Index: SimpleFlow.java
===================================================================
RCS file:
/home/cvs/cocoon-2.1/src/blocks/javaflow/test/org/apache/cocoon/components/flow/java/test/SimpleFlow.java,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -r1.3 -r1.4
--- SimpleFlow.java 3 Jun 2004 12:43:28 -0000 1.3
+++ SimpleFlow.java 3 Jun 2004 14:30:39 -0000 1.4
@@ -15,9 +15,13 @@
*/
package org.apache.cocoon.components.flow.java.test;
+import java.util.Locale;
+
import org.apache.cocoon.components.flow.java.*;
import org.apache.cocoon.forms.FormContext;
-import java.util.Locale;
+/*import org.apache.lucene.analysis.standard.StandardAnalyzer;
+import org.apache.lucene.queryParser.QueryParser;
+import org.apache.lucene.search.*;*/
public class SimpleFlow extends AbstractSimpleFlow {
@@ -91,9 +95,27 @@
System.out.println("end of flow");
return new FooInner(12,12);
}
+
+ /*public void doTest() throws Exception {
+
+ // This causes an error -> The class can not be registered at first
call!!!
+ Query query = null;
+ Hits hits;
+ IndexSearcher searcher = null;
+ // end
+
+ while(true) {
+
+ this.sendPageAndWait("foo");
+
+ query = QueryParser.parse("foo", "bar", new StandardAnalyzer());
+ // here comes the problem, because searcher is null, which must
preserved by the continuation
+ hits = searcher.search(query);
+ }
+ }*/
}
-class FooInner /*extends AbstractSimpleFlow*/ {
+class FooInner {
public FooInner(int i, int j) {
}