Return-Path: Delivered-To: apmail-cocoon-dev-archive@www.apache.org Received: (qmail 28891 invoked from network); 10 Aug 2006 21:24:38 -0000 Received: from hermes.apache.org (HELO mail.apache.org) (209.237.227.199) by minotaur.apache.org with SMTP; 10 Aug 2006 21:24:38 -0000 Received: (qmail 34269 invoked by uid 500); 10 Aug 2006 21:24:36 -0000 Delivered-To: apmail-cocoon-dev-archive@cocoon.apache.org Received: (qmail 34197 invoked by uid 500); 10 Aug 2006 21:24:35 -0000 Mailing-List: contact dev-help@cocoon.apache.org; run by ezmlm Precedence: bulk list-help: list-unsubscribe: List-Post: Reply-To: dev@cocoon.apache.org List-Id: Delivered-To: mailing list dev@cocoon.apache.org Received: (qmail 34185 invoked by uid 99); 10 Aug 2006 21:24:35 -0000 Received: from asf.osuosl.org (HELO asf.osuosl.org) (140.211.166.49) by apache.org (qpsmtpd/0.29) with ESMTP; Thu, 10 Aug 2006 14:24:35 -0700 X-ASF-Spam-Status: No, hits=0.0 required=10.0 tests= X-Spam-Check-By: apache.org Received-SPF: pass (asf.osuosl.org: local policy) Received: from [195.225.171.136] (HELO session.it) (195.225.171.136) by apache.org (qpsmtpd/0.29) with ESMTP; Thu, 10 Aug 2006 14:24:25 -0700 Received: (qmail 22233 invoked from network); 10 Aug 2006 23:21:20 +0200 Received: from adsl-ull-92-215.41-151.net24.it (HELO ?192.168.1.4?) (maurizio@session.it@151.41.215.92) by 195.225.171.136 with AES256-SHA encrypted SMTP; 10 Aug 2006 23:21:20 +0200 Message-ID: <44DBA447.1090800@thebug.it> Date: Thu, 10 Aug 2006 23:25:27 +0200 From: Maurizio Pillitu User-Agent: Thunderbird 1.5.0.5 (X11/20060803) MIME-Version: 1.0 To: cocoon-dev@apache.org Subject: cocoon-javaflow in cocoon 2.2 Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit X-Virus-Checked: Checked by ClamAV on apache.org X-Spam-Rating: minotaur.apache.org 1.6.2 0/1000/N Hi everybody, me and Simone spent few days trying to obtain a working javaflow again in cocoon 2.2, and to understand how it works deeply; we would like to report our achievements and problems. We started trying to obtain a complete system (reloading, runtime instrumentation etc..). But then scaled down step by step and arrived to the problem which is stopping us right now. We are working with the flow class instrumented statically, as well as AbstractContinuable, FormInstance and the Invoker. The form shows up correctly, but when we submit the form, ClassCastException : Caused by: java.lang.ClassCastException: org.apache.cocoon.samples.flow.java.SimpleFlow at org.apache.cocoon.components.flow.java.Invoker.run(Invoker.java) at org.apache.commons.javaflow.bytecode.StackRecorder.execute(StackRecorder.java:95) at org.apache.commons.javaflow.Continuation.continueWith(Continuation.java:170) at org.apache.cocoon.components.flow.java.JavaInterpreter.handleContinuation(JavaInterpreter.java:182) at org.apache.cocoon.components.treeprocessor.sitemap.CallFunctionNode.invoke(CallFunctionNode.java:98) When the form is rendered, the JavaInterprer instanciates an Invoker to pass to the Continuation object; the Invoker is responsible to call the Javaflow method that has been passed by the JavaInterpreter, using reflection. Since the class must be enhanced, also the method.invoke instruction should be, but it seems that the BcelClassTransformer doesn't parse this case (In this part we has serious difficulties to understand the code because we're not to deep into the JVM bytecode specs and stuff like that). In fact, if we replace the "method.invoke(o)" with "o.method()" (no reflection involved) it works correctly. IIUC the core of the instrumentation is done into the rewrite method, that parses the bytecode operations and decides what to do; adding a block that identifies the invoke operation and adds a method call would work; we tried unluckily to implement it, maybe someone could help us to understand how to do it. As I said, we arrived to this error by scaling down our target, our first test was to enhance a simple Java class, out of cocoon environment, using the FilesystemAlterationMonitor, that monitors a certain folder (in this case the folder containing the class file of the Javaflow) and enhance it, if it has been changed. We found a ClassFormatException ( java.lang.ClassFormatError: Incompatible magic value -272646673 in class file jci/Simple ) trying to read the original bytecode of the class; debugging the code we discovered that the ReloadingListener is using a FileReader to read the bytecode of the class; the FileReader parses the byte stream depending on a certain char encoding. so the bytecode is not recognized by the classloader. Using a FileInputStream it works (ReloadingClassLoaderTestCase confirms; with the original FileReader implementation it fails). Then we tried to integrate the FilesystemAlterationMonitor with the cocoon classloader configuration, in order to automatically reload and enhance the Javaflows when changed, but we faced with some problems. - The FilesystemAlterationMonitor always notifies the changes of those classes that are enhanced; the check is based on file.getLastModified() value, but every time the value is lower then the last one, so the change notification is triggered. We didn't investigate more. - The FileResourceStore fails trying to get the file by the filesystem: private File getFile(final String pResourceName) { final String fileName = pResourceName.replace('/',File.separatorChar); return new File(root, fileName); } where pResourceName = "org.apache.cocoon.samples.flow.java.SimpleFlow"; changing the return statement to : return new File(root, fileName.replace('.',File.separatorChar).concat(".class")); it seems to work correctly. Before send some patches we'd like to know if we're investigating in the right direction or not. We can also provide our temporary changes to the javaflow poms in order to enhance the JavaInterpreter and the javaflow classes at build time, using the RewriteAntTask provided by commons-javaflow and some fix to the cocoon-javaflow-sample block. Regards, Maurizio and Simone