From: <or...@us...> - 2015-05-11 18:37:44
|
Revision: 285 http://sourceforge.net/p/bsf4oorexx/code/285 Author: orexx Date: 2015-05-11 18:37:41 +0000 (Mon, 11 May 2015) Log Message: ----------- 20150511 Initial JSR223 support. Modified Paths: -------------- trunk/bsf4oorexx.dev/cmpj.cmd trunk/bsf4oorexx.dev/source_java/Test.class trunk/org/rexxla/bsf/engines/rexx/RexxAndJava$1.class trunk/org/rexxla/bsf/engines/rexx/RexxAndJava$2.class trunk/org/rexxla/bsf/engines/rexx/RexxAndJava$ExitDelayed.class trunk/org/rexxla/bsf/engines/rexx/RexxAndJava$SyncPutGet.class trunk/org/rexxla/bsf/engines/rexx/RexxAndJava.class trunk/org/rexxla/bsf/engines/rexx/RexxAndJava.java trunk/org/rexxla/bsf/engines/rexx/RexxEngine.class trunk/org/rexxla/bsf/engines/rexx/RexxEngine.java trunk/org/rexxla/bsf/engines/rexx/RexxExtendClass.class Added Paths: ----------- trunk/bsf4oorexx.dev/source_java/RexxCompiledScript.class trunk/bsf4oorexx.dev/source_java/RexxScriptEngine.class trunk/bsf4oorexx.dev/source_java/RexxScriptEngineFactory.class trunk/org/rexxla/bsf/engines/rexx/jsr223/ trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.class trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.java trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngine.class trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngine.java trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngineFactory.class trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngineFactory.java Modified: trunk/bsf4oorexx.dev/cmpj.cmd =================================================================== --- trunk/bsf4oorexx.dev/cmpj.cmd 2015-05-11 18:27:13 UTC (rev 284) +++ trunk/bsf4oorexx.dev/cmpj.cmd 2015-05-11 18:37:41 UTC (rev 285) @@ -25,6 +25,7 @@ rem set default path to org.rexxla.bsf, 2005-06-02, ---rgf set path2engine=%path2root%\org\rexxla\bsf\engines\rexx +set path2jsr223=%path2root%\org\rexxla\bsf\engines\rexx\jsr223 set path2rexxlaBsf=%path2root%\org\rexxla\bsf @@ -103,4 +104,12 @@ javac %javacDefines% %source% %target% %javaSrc%\RexxConfiguration.java && copy %javaSrc%\RexxConfiguration* %path2engine% +@rem 2015-05-11 +set target=-target 1.6 +set source=-source 1.6 + +javac %javacDefines% %source% %target% %javaSrc%\RexxScriptEngine.java && copy %javaSrc%\RexxScriptEngine.* %path2jsr223% +javac %javacDefines% %source% %target% %javaSrc%\RexxScriptEngineFactory.java && copy %javaSrc%\RexxScriptEngineFactory* %path2jsr223% +javac %javacDefines% %source% %target% %javaSrc%\RexxCompiledScript.java && copy %javaSrc%\RexxCompiledScript* %path2jsr223% + endlocal Added: trunk/bsf4oorexx.dev/source_java/RexxCompiledScript.class =================================================================== (Binary files differ) Index: trunk/bsf4oorexx.dev/source_java/RexxCompiledScript.class =================================================================== --- trunk/bsf4oorexx.dev/source_java/RexxCompiledScript.class 2015-05-11 18:27:13 UTC (rev 284) +++ trunk/bsf4oorexx.dev/source_java/RexxCompiledScript.class 2015-05-11 18:37:41 UTC (rev 285) Property changes on: trunk/bsf4oorexx.dev/source_java/RexxCompiledScript.class ___________________________________________________________________ Added: svn:executable ## -0,0 +1 ## +* \ No newline at end of property Added: svn:mime-type ## -0,0 +1 ## +application/octet-stream \ No newline at end of property Added: trunk/bsf4oorexx.dev/source_java/RexxScriptEngine.class =================================================================== (Binary files differ) Index: trunk/bsf4oorexx.dev/source_java/RexxScriptEngine.class =================================================================== --- trunk/bsf4oorexx.dev/source_java/RexxScriptEngine.class 2015-05-11 18:27:13 UTC (rev 284) +++ trunk/bsf4oorexx.dev/source_java/RexxScriptEngine.class 2015-05-11 18:37:41 UTC (rev 285) Property changes on: trunk/bsf4oorexx.dev/source_java/RexxScriptEngine.class ___________________________________________________________________ Added: svn:executable ## -0,0 +1 ## +* \ No newline at end of property Added: svn:mime-type ## -0,0 +1 ## +application/octet-stream \ No newline at end of property Added: trunk/bsf4oorexx.dev/source_java/RexxScriptEngineFactory.class =================================================================== (Binary files differ) Index: trunk/bsf4oorexx.dev/source_java/RexxScriptEngineFactory.class =================================================================== --- trunk/bsf4oorexx.dev/source_java/RexxScriptEngineFactory.class 2015-05-11 18:27:13 UTC (rev 284) +++ trunk/bsf4oorexx.dev/source_java/RexxScriptEngineFactory.class 2015-05-11 18:37:41 UTC (rev 285) Property changes on: trunk/bsf4oorexx.dev/source_java/RexxScriptEngineFactory.class ___________________________________________________________________ Added: svn:executable ## -0,0 +1 ## +* \ No newline at end of property Added: svn:mime-type ## -0,0 +1 ## +application/octet-stream \ No newline at end of property Modified: trunk/bsf4oorexx.dev/source_java/Test.class =================================================================== (Binary files differ) Modified: trunk/org/rexxla/bsf/engines/rexx/RexxAndJava$1.class =================================================================== (Binary files differ) Modified: trunk/org/rexxla/bsf/engines/rexx/RexxAndJava$2.class =================================================================== (Binary files differ) Modified: trunk/org/rexxla/bsf/engines/rexx/RexxAndJava$ExitDelayed.class =================================================================== (Binary files differ) Modified: trunk/org/rexxla/bsf/engines/rexx/RexxAndJava$SyncPutGet.class =================================================================== (Binary files differ) Modified: trunk/org/rexxla/bsf/engines/rexx/RexxAndJava.class =================================================================== (Binary files differ) Modified: trunk/org/rexxla/bsf/engines/rexx/RexxAndJava.java =================================================================== --- trunk/org/rexxla/bsf/engines/rexx/RexxAndJava.java 2015-05-11 18:27:13 UTC (rev 284) +++ trunk/org/rexxla/bsf/engines/rexx/RexxAndJava.java 2015-05-11 18:37:41 UTC (rev 285) @@ -21,7 +21,7 @@ * * * <pre>------------------------ Apache Version 2.0 license ------------------------- - * Copyright (C) 2001-2014 Rony G. Flatscher + * Copyright (C) 2001-2015 Rony G. Flatscher * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -36,7 +36,7 @@ * limitations under the License. * ----------------------------------------------------------------------------- </pre> * - * @version 4.2.0, 2014-10-05 + * @version 4.2.1, 2015-05-09 * @author Rony G. Flatscher (<a href="http://www.wu-wien.ac.at">WU-Wien/Wirtschaftsuniversität Wien</a>, <a href="http://www.wu-wien.ac.at/english">http://www.wu-wien.ac.at/english</a>) */ @@ -48,6 +48,13 @@ */ /* + 2015-05-09, ---rgf, - added access to important Rexx objects and interpreter related information + - protected native Object jniGetLocalEnvironment0 + - protected native Object jniGetGlobalEnvironment0 + - protected native Object jniNil0 + - protected native long jniInterpreterVersion0 + - protected native long jniLanguageLevel0 + 2014-10-04, ---rgf, - add subfunctions that return a reference to a java.lang.String object or a NetRexx object, if such a value needs to be returned (rather than turning it into a Rexx string), added subfunctions: @@ -319,7 +326,7 @@ /** Version string indicating version of this class (majorVersion*100+minorVersion * concatenated with a dot and the sorted date of last change. */ - static final public String version = "420.20141005"; + static final public String version = "421.20150509"; static final private String pkgName = "org.rexxla.bsf.engines.rexx"; @@ -841,10 +848,12 @@ protected native int jniRexxTerminateInterpreterInstance (String rii_ID); // use Terminate(), but *must* be issued from the original thread context + // ------------------ JNI functions meant to be accessed by Java exit handlers only! + // (these jni functions need a properly set up opaque slot argument!) + // rgf, 2012-02-08, used for allowing exit and command handlers to interact with their RexxExitContext // for raising conditions and querying/setting variables. // - protected native void jniRaiseCondition (Object[] slot, String conditionName, String description, Object[] additional, Object result); protected native void jniRaiseException (Object[] slot, long definedErrorNumber, Object[] substitutions); protected native void jniRaiseException0 (Object[] slot, long definedErrorNumber); @@ -853,7 +862,7 @@ protected native Object jniGetContextVariable(Object[] slot, String variableName); protected native void jniSetContextVariable(Object[] slot, String variableName, Object variableValue); - // rgf, 2012-02-11 + // rgf, 2012-02-11: for RexxHandler access only (these jni functions need a properly set up opaque slot argument!) protected native boolean jniCheckCondition (Object[] slot); protected native void jniClearCondition (Object[] slot); protected native Object jniGetConditionInfo (Object[] slot); @@ -861,30 +870,40 @@ protected native void jniSetThreadTrace (Object[] slot, boolean state); protected native void jniHaltThread (Object[] slot); - // rgf, 2012-02-12 + // rgf, 2012-02-12: for RexxHandler access only (these jni functions need a properly set up opaque slot argument!) protected native void jniDropContextVariable(Object[] slot, String variableName); - // rgf, 2012-02-18 + // rgf, 2012-02-18: for RexxHandler access only (these jni functions need a properly set up opaque slot argument!) protected native void jniSetContextVariableToNil(Object[] slot, String variableName); - // rgf, 2012-02-19 + // rgf, 2012-02-19: for RexxHandler access only (these jni functions need a properly set up opaque slot argument!) protected native Object jniGetCallerContext (Object[] slot); protected native Object jniGetAllContextVariables(Object[] slot); - // rgf, 2012-02-24 + // rgf, 2012-02-24: for RexxHandler access only (these jni functions need a properly set up opaque slot argument!) protected native Object jniGetLocalEnvironment(Object[] slot); protected native Object jniGetGlobalEnvironment(Object[] slot); - - // rgf, 2012-02-25 + // rgf, 2012-02-25: for RexxHandler access only (these jni functions need a properly set up opaque slot argument!) protected native Object jniNil(Object[] slot); protected native long jniInterpreterVersion(Object[] slot); protected native long jniLanguageLevel (Object[] slot); - // rgf, 2014-03-29 protected native String jniProcEnvironment(int function, String envName, String envValue); + // ------------------ allow fetching a few important Rexx objects resp. Rexx interpreter related information + // rgf, 2015-05-09 + protected native Object jniGetLocalEnvironment0 (String rii_ID); + protected native Object jniGetGlobalEnvironment0(String rii_ID); + protected native Object jniNil0 (String rii_ID); + protected native long jniInterpreterVersion0 (String rii_ID); + protected native long jniLanguageLevel0 (String rii_ID); + + + + + /** rgf, 2003-01-15, used for allowing the BSF4ooRexx-DLL to get at *env, *obj and then to mid etc. * */ protected native int jniInitialize4Rexx() ; Modified: trunk/org/rexxla/bsf/engines/rexx/RexxEngine.class =================================================================== (Binary files differ) Modified: trunk/org/rexxla/bsf/engines/rexx/RexxEngine.java =================================================================== --- trunk/org/rexxla/bsf/engines/rexx/RexxEngine.java 2015-05-11 18:27:13 UTC (rev 284) +++ trunk/org/rexxla/bsf/engines/rexx/RexxEngine.java 2015-05-11 18:37:41 UTC (rev 285) @@ -14,7 +14,7 @@ * using the RexxSAA interface. * * <pre>------------------------ Apache Version 2.0 license ------------------------- - * Copyright (C) 2001-2014 Rony G. Flatscher + * Copyright (C) 2001-2015 Rony G. Flatscher * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -29,7 +29,7 @@ * limitations under the License. * ----------------------------------------------------------------------------- </pre> * - * @version 4.5.0, 20140703 + * @version 4.5.1, 20150509 * @author Rony G. Flatscher (<a href="http://www.wu-wien.ac.at">WU-Wien/Wirtschaftsuniversität Wien</a>, <a href="http://www.wu-wien.ac.at/english">http://www.wu-wien.ac.at/english</a>) * */ @@ -37,6 +37,13 @@ /* last change: $Revision: 546 $ $Author: rony $ $Date: 2009-10-20 20:45:19 +0200 (Tue, 20 Oct 2009) $ + 2015-05-09, ---rgf, - added public methods + - getLocalEnvironment() ... returns .local + - getPublicEnvironment() ... returns .environment + - getNil() ... returns .nil + - getInterpreterVersion() ... returns long, where the least significant three bytes contain the version encoded + - getLanguageVersion() ... returns long, where the least significant two bytes contain the version encoded + 2014-07-03, ---rgf, - make sure that RexxProxy objects are always passed as Java objects in arguments; adapt apply() as well to pass through RexxProxy objects in arguments @@ -131,7 +138,7 @@ /** Version string indicating version of this class (majorVersion*100+minorVersion * concatenated with a dot and the sorted date of last change. */ - static final public String version = "450.20140703"; + static final public String version = "451.20150909"; /** If terminate() was invoked, then this instance must not be used anymore. */ @@ -254,6 +261,93 @@ + /** Get the ooRexx <code>.local</code> directory. + * + * @return a <code>RexxProxy</code> allowing access to the ooRexx <code>.local</code> directory + * @since 2015-05-09 + */ + public Object getLocalEnvironment() + { +System.err.println(this+".getLocalEnvrionment(), before doing a \"return rexxInterface.jniGetLocalEnvironment(rii_ID);\" ..."); + if (rii_ID==null) // Rexx interpreter instance (RII) not yet created, create it! + { + throw new NullPointerException("\"rii_ID\" (Rexx interpereter instance ID) null, Rexx interpreter instance not yet created (just eval() or apply() a script))"); + } + + return rexxInterface.jniGetLocalEnvironment0(rii_ID); + } + + /** Get the ooRexx <code>.environment</code> directory. + * + * @return a <code>RexxProxy</code> allowing access to the ooRexx <code>.environment</code> directory + * @since 2015-05-09 + */ + public Object getGlobalEnvironment() + { + if (rii_ID==null) // Rexx interpreter instance (RII) not yet created, create it! + { + throw new NullPointerException("\"rii_ID\" (Rexx interpereter instance ID) null, Rexx interpreter instance not yet created (just eval() or apply() a script))"); + } + return rexxInterface.jniGetGlobalEnvironment0(rii_ID); + } + + /** Get the ooRexx <code>.nil</code> object. + * + * @return a <code>RexxProxy</code> representint the ooRexx <code>.nil</code> sentinel object + * @since 2015-05-09 + */ + public Object getNil() + { + if (rii_ID==null) // Rexx interpreter instance (RII) not yet created, create it! + { + throw new NullPointerException("\"rii_ID\" (Rexx interpereter instance ID) null, Rexx interpreter instance not yet created (just eval() or apply() a script))"); + } + return rexxInterface.jniNil0(rii_ID); + } + + + /** (Copied from the ooRexx <code>rexxpg.pdf</code> documentation) "Returns + * the version of the interpreter. The returned version is + * encoded in the 3 least significant bytes of the returned value, + * using 1 byte each for the interpreter version, release, and revision + * values. For example, on a 32-bit platform, this value would be + * <code>0x00040000</code> for version 4.0.0." + * + * @return the ooRexx interpreter version + * @since 2015-05-09 + */ + public long getInterpreterVersion() + { + if (rii_ID==null) // Rexx interpreter instance (RII) not yet created, create it! + { + throw new NullPointerException("\"rii_ID\" (Rexx interpereter instance ID) null, Rexx interpreter instance not yet created (just eval() or apply() a script))"); + } + return rexxInterface.jniInterpreterVersion0(rii_ID); + } + + + /** (Copied from the ooRexx <code>rexxpg.pdf</code> documentation) "Returns the language level of + * the interpreter. The returned language level is encoded in the 2 least + * significant bytes of the returned value, using 1 byte each for the + * interpreter version, release, and revision values. For example, on a 32-bit + * platform, this value would be <code>0x00000603</code> for language level 6.03." + * + * @return the ooRexx language level + * @since 2015-05-09 + */ + public long getLanguageLevel() + { + if (rii_ID==null) // Rexx interpreter instance (RII) not yet created, create it! + { + throw new NullPointerException("\"rii_ID\" (Rexx interpereter instance ID) null, Rexx interpreter instance not yet created (just eval() or apply() a script))"); + } + return rexxInterface.jniLanguageLevel0(rii_ID); + } + + + + + /** Evaluates (executes) a piece of Rexx code * (can be a whole program as well) * <em>without</em> any Java-supplied arguments and returns the result. Modified: trunk/org/rexxla/bsf/engines/rexx/RexxExtendClass.class =================================================================== (Binary files differ) Added: trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.class =================================================================== (Binary files differ) Index: trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.class =================================================================== --- trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.class 2015-05-11 18:27:13 UTC (rev 284) +++ trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.class 2015-05-11 18:37:41 UTC (rev 285) Property changes on: trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.class ___________________________________________________________________ Added: svn:executable ## -0,0 +1 ## +* \ No newline at end of property Added: svn:mime-type ## -0,0 +1 ## +application/octet-stream \ No newline at end of property Added: trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.java =================================================================== --- trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.java (rev 0) +++ trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.java 2015-05-11 18:37:41 UTC (rev 285) @@ -0,0 +1,493 @@ +package org.rexxla.bsf.engines.rexx.jsr223; +import java.util.Vector; +import javax.script.*; + +import org.apache.bsf.BSFException; // BSF support + +import org.rexxla.bsf.engines.rexx.RexxEngine; +import org.rexxla.bsf.engines.rexx.RexxException; +import org.rexxla.bsf.engines.rexx.RexxProxy; + +/** Class that extends the <code>javax.script.CompiledScript</code> class and implements + * the <code>javax.script.Invocable</code> interface as this only makes sense in this + * class for {@link public <T> T getInterface(Class<T> clasz)}. Therefore the author + * (Rony G. Flatscher) who served on the JSR-223 specification committee) thinkgs that the documentation + * in <code>javax.script.Invocable</code> is false, as it states that <code>Invocable</code> gets implemented by a + * <code>ScriptEngine</code>, somehow indicating it has to operate on some "state" of the script engine. + * <br>Please note: the JSR-223 specification does not imply that ScriptEngine should implement this + * interface! + * <br>The [oo]Rexx implementation of JSR-223 tries to be as flexible as possible and also implements + * this interface in its implementation of <code>ScriptEngine</code> sharing as much code between + * the tow (and caching compiled scripts for invoking the aforementioned method in a sensible way. + * + * @author Rony G. Flatscher + * @since 2015-05-11 + * + */ +class RexxCompiledScript extends CompiledScript implements Invocable +{ + + private static final boolean bDebug=false; // true; // false; // true; + + /** Field that refers to the RexxScriptEngine instance which created this RexxCompiledScript. */ + RexxScriptEngine rse; + + + /** If set to <code>true</code> the <code>BSFException</code> (may contain a + * <code>RexxException</code> as cause) will be used to create and throw the <code>ScriptException</code>. + * If set to <code>false</code> the (Rexx formatted) message and the line number, if available, are used + * to create and throw the <code>ScriptException</code>. + */ + boolean bSupplyBSFExceptionObject=false; + + /** Getter for the Rexx script which got compiled (tokenized). + * @return the string representing of the compiled Rexx script + */ + public boolean getSupplyBSFExceptionObject() + { + return bSupplyBSFExceptionObject; + } + + /** Setter for the Rexx script which got compiled (tokenized). + * @return the string representing of the compiled Rexx script + */ + public void setSupplyBSFExceptionObject(boolean newValue) + { + bSupplyBSFExceptionObject=newValue; + } + + + + /** The filename used for evaluating (executing) the script or invoking functions or methods from the script */ + String filename; + + public String getFilename() + { + return filename; + } + + /** Getter for the Rexx script which got compiled (tokenized). + * @return the string representing of the compiled Rexx script + */ + + /** The script that was compiled (tokenized). */ + String scriptSource; + + /** Getter for the Rexx script which got compiled (tokenized). + * @return the string representing of the compiled Rexx script + */ + public String getScriptSource() + { + return scriptSource; + } + + /** The RexxProxy representing the compiled (tokenized) script (a Rexx routine object). */ + RexxProxy rexxScriptObject; + + /** Getter for the RexxProxy representing the Rexx routine object the script got compiled (tokenized) into. + * @return a RexxProxy representing the Rexx routine object + */ + public RexxProxy getScriptObject() + { + return rexxScriptObject; + } + + + /** A RexxProxy representing the script's package (a Rexx package object). */ + RexxProxy rexxPackageObject; + + /** Getter for the RexxProxy representing the Rexx routine object the script got compiled (tokenized) into. + * @return a RexxProxy representing the Rexx package object of this compiled script + */ + public RexxProxy getPackageObject() + { + return rexxPackageObject; + } + + + + RexxCompiledScript(RexxScriptEngine scriptEngine, + String scriptSource, + String filename, + boolean bSupplyBSFExceptionObject, + RexxProxy scriptRexxProxy, + RexxProxy scriptRexxPackage) + { + super(); + this.rse =scriptEngine; + this.scriptSource =scriptSource; + this.filename =filename; + this.bSupplyBSFExceptionObject=bSupplyBSFExceptionObject; + this.rexxScriptObject =scriptRexxProxy; + this.rexxPackageObject =scriptRexxPackage; + } + + /** Executes the program stored in this RexxCompiledScript object. + */ + public Object eval(ScriptContext sc) throws ScriptException + { +if (bDebug==true) { System.err.println("---> RCS ---> eval(), sc=["+sc+"]");} + if (sc==null) + { + throw new NullPointerException("Received \"ScriptContext sc\" argument null"); + } + + Object arrArgV[]; + try + { + arrArgV=createArgV((Object[])sc.getAttribute(ScriptEngine.ARGV), sc, rse); + } + catch (BSFException exc) + { + throw createScriptException(exc); + } + +if (bDebug==true) +{ + System.err.println("\t eval(), double check, arrArgV.length=["+arrArgV.length+"]"); + for (int i=0;i<arrArgV.length;i++) + { + System.err.println("\t\tarrArgV["+i+"]=["+arrArgV[i]+"]"); + } +} + + String filename=(String) sc.getAttribute(ScriptEngine.FILENAME); + if (filename==null) // no filename given + { + filename="filename_created_by_"+this.toString().replace('.','_').replace('@','-')+"_at_"+RexxScriptEngine.getGMTFormattedDate4Filename(); + } +if (bDebug==true) { System.err.println("---> RCS ---> filename=["+filename+"]");} + + try { +if (bDebug==true) { System.err.println("... eval(): before rse.updateRexxEngine(sc)");} + + rse.updateRexxEngine(sc); // make sure BSF.CLS support in JNI available; .input, .output, .error set accordingly +if (bDebug==true) +{ + System.err.println("... eval(): after rse.updateRexxEngine(sc)"); + for (int i=0;i<arrArgV.length;i++) + { + System.err.println("... ... RexxCompiledScript.eval(), arrArgV["+i+"]=["+arrArgV[i]+"]"); + } + System.err.println("... eval(): rexxScriptObject=["+rexxScriptObject+"]"); +} + return rexxScriptObject.sendMessage1("CALLWITH", arrArgV); // execute routine object + } + catch (BSFException exc) + { + throw createScriptException(exc); + } + } + + + + /** Returns the ScriptEngine whose compile method created this CompiledScript. + */ + public ScriptEngine getEngine() + { + return rse; + } + + +// ----------------------------------------------------------------------------------------------------- +// Invocable methods + /** Returns an implementation of an interface using functions compiled in the interpreter. + */ + public <T> T getInterface(Class<T> clasz) + { + + if (clasz==null) + { + throw new IllegalArgumentException("Received 'clasz' argument is null"); + } + if (! (clasz.isInterface()) ) + { + throw new IllegalArgumentException("Received 'clasz' argument is not an interface class"); + } + + ScriptContext sc=rse.getContext(); // get default ScriptContext +/* + // define a Rexx class that gets the routine object and its package object + // to dispatch Interface methods iva publich Rexx routines in its unknown method + String code= + "use arg rexxScript, rexxPackage, scriptContext \n" + + " -- create and return dispatcher object \n" + + "return .jsr223.DispatchInterfaceMethodsToPublicRexxRoutines~new(rexxScript, rexxPackage, scriptContext) \n" + + " \n" + + "::requires BSF.CLS -- get Java camouflaging support \n" + + " \n" + + " -- dispatcher class for Invocable' <T> T getInterface(Class<T> clasz) \n" + + "::class 'jsr223.DispatchInterfaceMethodsToPublicRexxRoutines' \n" + + " \n" + + "::method init -- constructor \n" + + " expose rexxScriptObject rexxScriptPackage jsr223ScriptContext \n" + + " use strict arg rexxScriptObject, rexxScriptPackage, jsr223ScriptContext \n" + + " \n" + + "::method unknown -- dispatch public routines instead \n" + + " expose rexxScriptObject rexxScriptPackage jsr223ScriptContext \n" + + " use strict arg methName, methArrArgv -- unknown message name and its arguments \n" + + " \n" + + " pubRoutines=rexxScriptPackage~publicRoutines -- get the public routines directory \n" + + " if pubRoutines~hasentry(methName)=.false then -- if public routine not available raise error \n" + + " raise syntax 93.1 array (methName) -- routine not found! \n" + + " \n" + + " -- add ScriptContext to BSF4ooRexx' slot argument (a Rexx directory added as last argument on callbacks) \n" + + " methArrArgv~lastItem~setentry('SCRIPTCONTEXT', jsr223ScriptContext) -- add ScriptContext \n" + + " \n" + + " pubRoutines~callWith(methName, methArrArgv) -- invoke routine \n" + + " if var('RESULT') then return result -- if a result object got returned, return it \n" ; + + Vector argVec=new Vector(); // define and set the arguments + argVec.add(rexxScriptObject); + argVec.add(rexxPackageObject); + // get and supply the default ScriptContext + argVec.add(sc); // supply it as last argument +*/ + + RexxProxy rp; + try { + // make sure BSF.CLS support in JNI available; .input, .output, .error set accordingly + rse.updateRexxEngine(sc); + + // create and get the ooRexx dispatching object, working on the available public routines + // rp=(RexxProxy) rse.getBsfRexxEngine().apply(this.toString()+"_create_interface_to_public_routine_dispatching_object", 0, 0, code, null, argVec); // new Vector(), new Vector()); + +if (bDebug==true) { System.err.println("---> ---> RexxCompiledScript() BEVOR trying to get access to object."); } + + rp=(RexxProxy) rse.getRoutineWrapper().sendMessage3("CALL", getScriptObject(), getPackageObject(), sc); + +if (bDebug==true) { System.err.println("<--- <--- RexxCompiledScript() AFTER trying to get access to object."); } + } + catch (Exception exc) // if a BSFException, return null + { + // cannot throw a ScriptException because it would violate the Interface definition of this method; + // try to inform the user anyway and give as much useful information as possible about the exception + System.err.println("Exception ["+exc+"] raised while trying to create dispatching object, cause: ["+exc.getCause()+"]"); + System.err.println("Exception ["+exc+"], stack trace:"); + exc.printStackTrace(); + System.err.println("Exception ["+exc+"], returning null to indicate failure"); + return null; + } + + // now create a JavaProxy where the Interface method invocations will forward a message by + // the name of the invoked method to the contained Rexx object + Object[] interfaces = new Object[1]; + interfaces[0]=clasz; + + return (T) rp.newJavaProxyInstance(interfaces); // create and return the Java proxy for the interface + } + + + /** Returns an implementation of an interface using member functions of a scripting object compiled in the interpreter. + * Uses the implementation in {@link RexxScriptEngine} to not duplicate code (and thereby making maintenance safer). + */ + public <T> T getInterface(Object thiz, Class<T> clasz) + { + +// TODO: - use a special class to embed thiz, which then adds the default SC as (second to?) last argument, such that +// the methods can get access to the defualt SC? +// - add an attribute jsr223ScriptContext, such that it can be changed later on? + + // use the implementation in RexxScriptEngine as this method is not CompiledScript related + return rse.getInterface(thiz,clasz); + } + + /** Used to call top-level procedures and functions (accessible public Rexx routines) defined in scripts. */ + public Object invokeFunction(String name, Object... args) throws ScriptException, NoSuchMethodException + { + if (name==null) + { + throw new NullPointerException("Received 'name' argument (function name) is null"); + } + + try { + RexxProxy publicRoutines=(RexxProxy) rexxPackageObject.sendMessage0("PUBLICROUTINES"); + String result=(String) publicRoutines.sendMessage1("HASENTRY", name); + +if (bDebug==true) { System.err.println("... ["+this+"]: checking for public routine \""+name+"\": result=["+result+"], result.getClass()="+result.getClass());} + + if ( result.equals("0")==true) // returned .false ? + { + throw new NoSuchMethodException("Received 'name' argument \""+name+"\" does not denote an existing, public Rexx routine"); + } + + // get the public routine, prepare arguments, invoke it + Object arrArgV[]=createArgV(args, rse.getContext(), rse); // supply default context + RexxProxy routine=(RexxProxy) publicRoutines.sendMessage1("ENTRY",name); // get routine + return routine.sendMessage1("CALLWITH",arrArgV); + } + catch (Exception exc) + { + // throw new ScriptException(exc); + throw createScriptException(exc); // create ScriptException and throw it + } + } + + + /** Calls a method on a script object compiled during a previous script execution, which is retained in the state of the ScriptEngine. + * Uses the implementation in {@link RexxScriptEngine} to not duplicate code (and thereby making maintenance safer). + * + */ + public Object invokeMethod(Object thiz, String name, Object... args) throws ScriptException, NoSuchMethodException + { + // use the implementation in RexxScriptEngine as this method is not CompiledScript related + return rse.invokeMethod(thiz, name, args); + } + + + // --------------- utility methods + + ScriptException createScriptException(Exception exc) + { + if (bSupplyBSFExceptionObject==true ) // return a plain ScriptException supplying the causing exception + { + return new ScriptException(exc); + } + + // just a plain BSFException or RexxException without the Rexx condition object: return causing exception + if (! (exc instanceof RexxException) || (((RexxException)exc).getRexxConditionObject()==null) ) + { + return new ScriptException(exc); + } + + // o.k., we are supposed to fill in as much information as possible, instead of supplying the BSFException + RexxProxy rco=((RexxException)exc).getRexxConditionObject(); // get Rexx condition object + + // TODO: create the values + String message =createRexxLikeConditionMessage(rco); + String filename="n/a"; + String position=null; + try { + filename=(String)rco.sendMessage0("PROGRAM"); + position=(String)rco.sendMessage0("POSITION"); + } + catch (Exception bsfexc) {} + + int line =-1; // indicate unknown line + + if (position instanceof String) + { + line= Integer.valueOf(position).intValue(); + } + return new ScriptException(message, filename, line); + } + + + + /** Utility method which should (after debugging) be moved to RexxException to serve all Java clients. + * Modelled after <code>BSF4ooRexx.cc</code>'s <code>RgfCreateRexxlikeErrorInfo</code> function. + * @param rco a Rexx proxy allowing access to the Rexx condtion object (a Rexx directory) + */ + String createRexxLikeConditionMessage(RexxProxy rco) + { + StringBuffer sb=new StringBuffer(); + String conditionName=null; + + try + { + conditionName=(String) rco.sendMessage0("CONDITION"); + if (conditionName.equals("SYNTAX")) // format a syntax condition + { + // line # 1 + sb.append((String) ((RexxProxy) rco.sendMessage0("TRACEBACK")).sendMessage0("FIRSTITEM")); + sb.append('\n'); + + // line # 2 + sb.append(String.format("Error %s running %s line %s: %s", + (String) rco.sendMessage0("RC"), + (String) rco.sendMessage0("PROGRAM"), + (String) rco.sendMessage0("POSITION"), + (String) rco.sendMessage0("ERRORTEXT"))); + sb.append('\n'); + sb.append(String.format("Error %s: %s", + (String) rco.sendMessage0("CODE"), + (String) rco.sendMessage0("MESSAGE"))); + } + + else if (conditionName.equals("NOVALUE")) // format a novalue condition + { + // line # 1 + sb.append((String) ((RexxProxy) rco.sendMessage0("TRACEBACK")).sendMessage0("FIRSTITEM")); + sb.append('\n'); + + // line # 2 + sb.append(String.format("Rexx condition [%s] raised for variable [%s] running %s line: %s", + conditionName, + (String) rco.sendMessage0("DESCRIPTION"), + (String) rco.sendMessage0("PROGRAM"), + (String) rco.sendMessage0("POSITION"))); + } + // as of ooRexx 4.2.0 for "failure", "error", "user": only entries CONDITION, RC (for failure and error) available + else + { + // line # 1 + sb.append(String.format("Rexx condition [%s] raised running %s", + conditionName, filename )); + + if (! (conditionName.startsWith("USER"))) // a failure or error condition has a RC value going with it + { + sb.append(String.format(", return code [%s]", + (String) rco.sendMessage0("RC"))); + } + + } + } + catch (Exception exc) + { + throw new IllegalArgumentException("accessing argument \"rco\" with conditionname ["+conditionName+"] caused the exception: ["+exc+"]"); + } + return sb.toString(); + } + + + /** Creates and returns the argument array, append ScriptContext sc as last argument + * for the Rexx script to be able to fetch it. As of ooRexx 4.2.0 the routine's <code>CALLWITH</code> + * method sends a <code>MAKEARRAY</code> message which will compact the Java array by removing <code>null</code> + * values (behaviour of {@link ArrayWrapper} to mimickry the ooRexx <code>Array MAKEARRAY</code> behaviour + * (ooRexx arrays are capapble of distinguishing whether an entry is empty or is explicitly set + * to <code>.nil</code>). To keep the argument array intact when there are Java array entries with the + * value <code>null</code> a {@link RexxProxy} for the ooRexx <code>.nil</code> object is used for replacement. + * the Rexx code fetching such an argument needs to unwrap the contained ooRexx <code>.nil</code> object using + * the external BSF function <code>BsfRexxProxy(rexxProxy,"ooRexxObject")</code>. + * + * @param args Object array with arguments to be supplied to the Rexx script + * @param sc ScriptContext to be appended to the arguments for the Rexx script + * @return an Object array containing all arguments to be passed on to the Rexx script + */ + static Object[] createArgV(Object[] args, ScriptContext sc, RexxScriptEngine rse) throws ScriptException, BSFException + { + int argsLength= (args!=null ? args.length : 0); + Object arrArgV[]=new Object[argsLength+1]; + int i=0; + + if (args!=null && args.length>0) // if ARGV array is given and has entries, then create argument vector + { + Object rexxNil=rse.getNil(); + for (i=0; i<args.length; i++) // loop over arguments + { + +if (bDebug) { System.err.println("===> createArgV(), args["+i+"]=["+args[i]+"]"); } + + Object o=args[i]; + arrArgV[i]=( o==null ? rexxNil : o ); + } + } + + // add as last argument, so scripts can always fetch the current ScriptContext; + // make sure last argument is a Rexx directory, with an entry "SCRIPTCONTEXT" storing the ScriptContext object + // (this way Rexx routines - even those invoked from JavaProxy invocations - can rely that + // the last argument is a directory containing an entry "SCRIPTCONTEXT") + +if (bDebug) +{ + System.err.println("===> createArgV(), about to add ScriptContext argument!"); + RexxProxy gcd=rse.getCreateDirectory(); + System.err.println(" gcd=["+gcd+"]"); +} + + arrArgV[i]=rse.getCreateDirectory().sendMessage2("CALL","SCRIPTCONTEXT",sc); + return arrArgV; + } + + +} Property changes on: trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxCompiledScript.java ___________________________________________________________________ Added: svn:executable ## -0,0 +1 ## +* \ No newline at end of property Added: trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngine.class =================================================================== (Binary files differ) Index: trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngine.class =================================================================== --- trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngine.class 2015-05-11 18:27:13 UTC (rev 284) +++ trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngine.class 2015-05-11 18:37:41 UTC (rev 285) Property changes on: trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngine.class ___________________________________________________________________ Added: svn:executable ## -0,0 +1 ## +* \ No newline at end of property Added: svn:mime-type ## -0,0 +1 ## +application/octet-stream \ No newline at end of property Added: trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngine.java =================================================================== --- trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngine.java (rev 0) +++ trunk/org/rexxla/bsf/engines/rexx/jsr223/RexxScriptEngine.java 2015-05-11 18:37:41 UTC (rev 285) @@ -0,0 +1,1042 @@ +package org.rexxla.bsf.engines.rexx.jsr223; +import javax.script.*; + +import java.util.Vector; + +import java.io.BufferedReader; +import java.io.IOException; +import java.io.Reader; +import java.io.Writer; + +import java.util.Date; +import java.text.SimpleDateFormat; +import java.util.TimeZone; + +import java.util.List; +import java.util.Vector; + +import org.apache.bsf.BSFManager; // BSF support +import org.apache.bsf.BSFException; // BSF support + +import org.rexxla.bsf.engines.rexx.RexxEngine; +import org.rexxla.bsf.engines.rexx.RexxProxy; +import org.rexxla.bsf.engines.rexx.RexxException; + + +/** Class that extends extends the <code>javax.script.ScriptEngine</code> class and implements the + * <code>javax.script.Compilalbe</code> and * the <code>javax.script.Invocable</code> interface, + * although the latter one would only make sense in {@link RexxCompiledScript} class, because of the + * {@link public <T> T getInterface(Class<T> clasz)} method. Therefore the author (Rony + * G. Flatscher who served on the JSR-223 specification committee) thinks that the documentation + * in <code>javax.script.Invocable</code> is false, as it states that <code>Invocable</code> gets implemented by a + * <code>ScriptEngine</code>, somehow indicating it has to operate on some "state" of the script engine. + * <br>Please note: the JSR-223 specification does not imply that ScriptEngine should implement this + * interface! + * <br>The [oo]Rexx implementation of JSR-223 tries to be as flexible as possible and also implements + * this interface in its implementation of <code>ScriptEngine</code> sharing as much code between + * the tow (and caching compiled scripts for invoking the aforementioned method in a sensible way. + * + * @author Rony G. Flatscher + * @since 2015-05-11 + * + */ +public class RexxScriptEngine extends AbstractScriptEngine implements Compilable, Invocable +{ + + /* if set to false the Java compiler will remove all bDebug-controlled statements */ + static private final boolean bDebug=false; // true; // false; // true; + + // - define a public static flag that determines which version of the ScriptException should be used (passing on RexxException or supplying message, linenr, colnr?) + /** This controls whether ScriptExceptions should supply the <code>RexxException</code> object (extends <code>BSFException</code>) or fill in the ScriptException + * fields (message, line and column number, if present). Using <code>BSFException.getCause()</code> will return + * the <code>RexxException</code> object, that has a method <code>getRexxConditionObject</code> which is a <code>RexxProxy</code> for + * the Rexx directory (cf. the ooRexx condition object documentation for its entries). + * <br>If set to <code>false</code>, then an attempt is made to supply as much information according to + * the <code>ScriptException</code> constructors, which might ease generic script editors that use JSR223 script engines. + */ + public static boolean bSupplyBSFExceptionObject=true; + + /** Caches the latest reader fetched from the script context. ooRexx will store this in <code>.input</code>, such that + * it is not necessary to set this value each time a script gets invoked or evaluated. + */ + Reader cachedReader; + + /** Caches the latest writer fetched from the script context. ooRexx will store this in <code>.output</code>, such that + * it is not necessary to set this value each time a script gets invoked or evaluated. + */ + Writer cachedWriter; + + /** Caches the latest writer fetched from the script context. ooRexx will store this in <code>.error</code>, such that + * it is not necessary to set this value each time a script gets invoked or evaluated. + */ + Writer cachedErrorWriter; + + /** Caches the last compiled script. This is necessary in the case that <code>Invocation</code> methods + * get invoked (namely "<code><T> T getInterface(Class;<T> clasz)/code>") + * via the ScriptEngine as the <code>javax.script.Invocable</code> documentation (in + * the author's (Rony G. Flatscher) opinion, who also has served on the JSR-223 specification + * team for javax.script) erroneously states that <code>Invocable</code> should be implemented + * by a <code>ScriptEngine</code> rather than a CompiledScript</code>. + */ + RexxCompiledScript currentScript; + + /** Getter method for "current" (the latest evaluated) script. Due to the ooRexx architecture + * each script gets compiled (actually tokenized and its package set up) and will be stored in a field. + * Each script that gets evaluated will replace the {@link currentScript} object. + * Fetching this {@link RexxCompiledScript} allows one to execute it as many times as needed, but also + * use all of the implemented {@link Invocable} methods. + * + * @return the current (latest) {@link RexxCompiledScript} object or <code>null</code> if no script has + * been evaluated or compiled yet + */ + public RexxCompiledScript getCurrentScript() + { + return currentScript; + } + + + + /** Rexx code to dynamically require "<code>BSF.CLS</code>". This makes sure that the + * native part of <code>BSF4ooRexx</code> is set to support the camouflaging support from the beginning. + */ + public static final String dynamicallyRequireBSF=".context~package~addPackage(.package~new('BSF.CLS')); /* <-- injected by RexxScriptEngine.compile() */ "; + + // - define a public static flag that determines whether we should add a prolog statement to make sure that BSF.CLS gets required (dynamically in this case) + /** This controls whether the supplied Rexx scripts should get a dynamic requires statement prepended that + * makes sure that the Java support is present. This may cause runtime errors, if the first statement in the + * Rexx script is a hash-bang line (if present it must be the very first line, because the ooRexx interpreter + * removes it for execution). + */ + public static boolean bPrependDynamicRequiresStatement=true; + + + /** This controls whether the initial requires for 'BSF.CLS' has been carried out or not, which is necessary + * to allow the very first Rexx script to pass Java objects as arguments already. + */ + boolean bInitialBSFRequiresDone=false; + + + /** Stores the BSF Rexx engine which gets used to invoke the scripts */ + RexxEngine bsfRexxEngine; + + /** Getter method that returns the BSF scripting engine in use. + * @return the BSF Rexx engine used for this RexxScriptEngine + */ + public RexxEngine getBsfRexxEngine() + { + return bsfRexxEngine; + } + + private Object nil=null; + public Object getNil() + { + if (nil==null) + { + nil=bsfRexxEngine.getNil(); + } + return nil; + } + + + /** Stores the BSF Rexx manager that is used for loading the BSF Rexx engine. */ + BSFManager bsfMgr; + + /** Getter method that returns the BSF manager used for managing this BSF scripting engine. + * @return the BSF manager used for managing this RexxScriptEngine + */ + public BSFManager getBsfManager() + { + return bsfMgr; + } + + + /** Rexx code to create and return a Rexx routine object from Rexx code. */ + String rexxCreateRoutineCode= + "use strict arg name, code \n" + + "return .routine~new(name,code) \n" + + "::requires 'BSF.CLS' \n" ; + + /** <code>RexxProxy</code> for the Rexx routine created by the Rexx code stored in {@link rexxCreateRoutineCodeCode}. */ + private RexxProxy rexxCreateRoutine=null; + + /** Getter method to return {@link rexxCreateRoutineCode}. If {@link rexxCreateRoutineCode} is <code>null</code> + * the Rexx routine object will get created, stored and returned. + * @return the <code>RexxProxy</code> for the Rexx routine to create a Rexx directory (and optionally supply + * a single entry) + */ + RexxProxy getCreateRoutine() throws ScriptException + { +if (bDebug==true){ System.err.println("arrived: getCreateRoutine(), rexxCreateRoutine="+rexxCreateRoutine);} + if (rexxCreateRoutine!=null) + { + return rexxCreateRoutine; + } + + String filename="RexxScriptEngine_rexxCreateRoutineCode.rex"; + try + { + updateRexxEngine(null); + Vector args=new Vector(); + args.add("CreateRoutineCode"); + args.add(rexxCreateRoutineCode); + +if (bDebug==true){ System.err.println(" --- getCreateRoutine(), BEVOR bsfRexxEngine="+bsfRexxEngine+", rexxCreateRoutine="+rexxCreateRoutine);} + rexxCreateRoutine=(RexxProxy) bsfRexxEngine.apply(filename, 0, 0, rexxCreateRoutineCode, null, args); +if (bDebug==true){ System.err.println(" --- getCreateRoutine(), AFTER bsfRexxEngine="+bsfRexxEngine+", rexxCreateRoutine="+rexxCreateRoutine);} + } + catch (Exception exc) + { + // in this very initial phase of compilation (tokenization) of the Rexx script always supply the cause exception +if (bDebug==true) {exc.printStackTrace(); } + + throw new ScriptException(exc); // re-throw, wrap cause in script + } + return rexxCreateRoutine; + } + + + /** Rexx code to create and return a Rexx routine object from Rexx code. */ + String rexxMonitorWrapperCode= + " use arg rexxObject, scriptContext \n" + + " -- say 'in rexxMonitorWrapperCode prolog...' \n" + + " \n" + + " -- create and return dispatcher object \n" + + " return .DispatchWrapper~new(rexxObject, scriptContext) \n" + + " \n" + + " ::requires BSF.CLS -- get Java camouflaging support \n" + + " \n" + + " -- dispatcher class for Invocable' <T> T getInterface(Object thiz, Class<T> clasz) \n" + + " ::class 'DispatchWrapper' \n" + + " \n" + + " ::method init -- constructor \n" + + " expose rexxScriptObject jsr223ScriptContext \n" + + " use strict arg rexxScriptObject, jsr223ScriptContext \n" + + " \n" + + " -- add ScriptContext to slotDir (last) argument, forward method invocation \n" + + " ::method unknown -- dispatch public routines instead \n" + + " expose rexxScriptObject jsr223ScriptContext \n" + + " use strict arg methName, methArrArgv -- unknown message name and its arguments \n" + + " \n" + + " -- add ScriptContext to BSF4ooRexx' slot argument (a Rexx directory added as last argument on callbacks) \n" + + " methArrArgv~lastItem~setentry('SCRIPTCONTEXT', jsr223ScriptContext) -- add ScriptContext \n" + + " \n" + + " forward message (methName) to (rexxScriptObject) arguments (methArrArgv) -- forward message \n" ; + + /** <code>RexxProxy</code> for using an in-between (monitor) class for adding the <code>ScriptContext</code> + * to the slotDir directory added by BSF4ooRexx in Java call-back scenarios. + */ + private RexxProxy rexxMonitorWrapper=null; + + /** Getter method to return the ooRexx routine. If {@link rexxMonitorWrapper} is <code>null</code> + * the Rexx routine object will get created, stored and returned. + * @return the <code>RexxProxy</code> for the Rexx routine + */ + RexxProxy getMonitorWrapper() throws ScriptException + { +if (bDebug==true){ System.err.println("arrived: getMonitorWrapper(), rexxMonitorWrapper="+rexxMonitorWrapper);} + if (rexxMonitorWrapper!=null) + { + return rexxMonitorWrapper; + } + + try + { + updateRexxEngine(null); +/* + String filename="RexxScriptEngine_rexxMonitorWrapperCode.rex"; + Vector args=new Vector(); + args.add("MonitorWrapperCode"); + args.add(rexxMonitorWrapperCode); + +if (bDebug==true){ System.err.println(" --- getMonitorWrapper(), BEVOR bsfRexxEngine="+bsfRexxEngine+", rexxMonitorWrapper="+rexxMonitorWrapper);} + + rexxMonitorWrapper=(RexxProxy) bsfRexxEngine.apply(filename, 0, 0, rexxMonitorWrapperCode, null, args); +*/ + rexxMonitorWrapper=(RexxProxy) getCreateRoutine().sendMessage2("CALL", "MonitorWrapperCode", rexxMonitorWrapperCode); + + +if (bDebug==true){ System.err.println(" --- getMonitorWrapper(), AFTER bsfRexxEngine="+bsfRexxEngine+", rexxMonitorWrapper="+rexxMonitorWrapper);} + } + catch (Exception exc) + { + // in this very initial phase of compilation (tokenization) of the Rexx script always supply the cause exception +if (bDebug==true) {exc.printStackTrace(); } + + throw new ScriptException(exc); // re-throw, wrap cause in script + } + return rexxMonitorWrapper; + } + + /** Rexx code to create and return a Rexx routine object from Rexx code. */ + String rexxRoutineWrapperCode= + "use arg rexxScript, rexxPackage, scriptContext \n" + + " \n" + + "-- say '/// --> /// in rexxRoutineWrapperCode - prolog... arg()='arg() \n" + + " \n" + + " -- create and return dispatcher object \n" + + "return .DispatchToToPublicRoutines~new(rexxScript, rexxPackage, scriptContext) \n" + + " \n" + + "::requires BSF.CLS -- get Ja... [truncated message content] |