org.omegahat.Environment.GUITools
Class EvaluableInterfaceGenerator

java.lang.Object
  |
  +--org.omegahat.Environment.Compile.DynamicCompiler
        |
        +--org.omegahat.Environment.GUITools.EvaluableInterfaceGenerator
All Implemented Interfaces:
jas.RuntimeConstants
Direct Known Subclasses:
CastFunctionCall, UserClassGenerator

public class EvaluableInterfaceGenerator
extends DynamicCompiler
implements jas.RuntimeConstants

This class is responsible for generating new classes that can be used to connect the interpreted and Java worlds by allowing an Omegahat Function to be used to implement a Java interface class. An appropriate class implementing one or more interfaces is dynamically compiled with each method being implemented as a simple call to the function with its own arguments being passed directly to the function.

The code generated by this class is now thread-safe in that it uses an instance of FunctionCallArguments local to the method and passes this to the eval(List) method inherited from the FunctionListener base class.

See Also:
FunctionListener

Field Summary
protected  java.util.Vector interfaces
          A collection of the different interface Classes being implemented by the new class.
protected  java.lang.String separator
          Separator used when displaying a non-primitive class, used when creating method signatures.
static java.lang.String signaturePrefix
           
static java.lang.String signatureSuffix
           
protected  boolean useSuperClassConstructors
          Flag indicating whether the newly defined class should copy the constructors from its parent/base class (true) or not.
 
Fields inherited from class org.omegahat.Environment.Compile.DynamicCompiler
BOTH, classDef, className, debug, GET, output, packageName, SET, superClassName
 
Fields inherited from interface jas.RuntimeConstants
ACC_ABSTRACT, ACC_FINAL, ACC_INTERFACE, ACC_NATIVE, ACC_PRIVATE, ACC_PROTECTED, ACC_PUBLIC, ACC_STATIC, ACC_SUPER, ACC_SYNCHRONIZED, ACC_TRANSIENT, ACC_VOLATILE, CONSTANT_CLASS, CONSTANT_DOUBLE, CONSTANT_FIELD, CONSTANT_FLOAT, CONSTANT_INTEGER, CONSTANT_INTERFACEMETHOD, CONSTANT_LONG, CONSTANT_METHOD, CONSTANT_NAMEANDTYPE, CONSTANT_STRING, CONSTANT_UNICODE, CONSTANT_UTF8, JAVA_MAGIC, JAVA_MINOR_VERSION, JAVA_VERSION, opc_aaload, opc_aastore, opc_aconst_null, opc_aload, opc_aload_0, opc_aload_1, opc_aload_2, opc_aload_3, opc_anewarray, opc_areturn, opc_arraylength, opc_astore, opc_astore_0, opc_astore_1, opc_astore_2, opc_astore_3, opc_athrow, opc_baload, opc_bastore, opc_bipush, opc_breakpoint, opc_caload, opc_castore, opc_checkcast, opc_d2f, opc_d2i, opc_d2l, opc_dadd, opc_daload, opc_dastore, opc_dcmpg, opc_dcmpl, opc_dconst_0, opc_dconst_1, opc_ddiv, opc_dead, opc_dload, opc_dload_0, opc_dload_1, opc_dload_2, opc_dload_3, opc_dmul, opc_dneg, opc_drem, opc_dreturn, opc_dstore, opc_dstore_0, opc_dstore_1, opc_dstore_2, opc_dstore_3, opc_dsub, opc_dup, opc_dup_x1, opc_dup_x2, opc_dup2, opc_dup2_x1, opc_dup2_x2, opc_f2d, opc_f2i, opc_f2l, opc_fadd, opc_faload, opc_fastore, opc_fcmpg, opc_fcmpl, opc_fconst_0, opc_fconst_1, opc_fconst_2, opc_fdiv, opc_fload, opc_fload_0, opc_fload_1, opc_fload_2, opc_fload_3, opc_fmul, opc_fneg, opc_frem, opc_freturn, opc_fstore, opc_fstore_0, opc_fstore_1, opc_fstore_2, opc_fstore_3, opc_fsub, opc_getfield, opc_getstatic, opc_goto, opc_goto_w, opc_i2b, opc_i2c, opc_i2d, opc_i2f, opc_i2l, opc_i2s, opc_iadd, opc_iaload, opc_iand, opc_iastore, opc_iconst_0, opc_iconst_1, opc_iconst_2, opc_iconst_3, opc_iconst_4, opc_iconst_5, opc_iconst_m1, opc_idiv, opc_if_acmpeq, opc_if_acmpne, opc_if_icmpeq, opc_if_icmpge, opc_if_icmpgt, opc_if_icmple, opc_if_icmplt, opc_if_icmpne, opc_ifeq, opc_ifge, opc_ifgt, opc_ifle, opc_iflt, opc_ifne, opc_ifnonnull, opc_ifnull, opc_iinc, opc_iload, opc_iload_0, opc_iload_1, opc_iload_2, opc_iload_3, opc_imul, opc_ineg, opc_instanceof, opc_int2byte, opc_int2char, opc_int2short, opc_invokeinterface, opc_invokenonvirtual, opc_invokespecial, opc_invokestatic, opc_invokevirtual, opc_ior, opc_irem, opc_ireturn, opc_ishl, opc_ishr, opc_istore, opc_istore_0, opc_istore_1, opc_istore_2, opc_istore_3, opc_isub, opc_iushr, opc_ixor, opc_jsr, opc_jsr_w, opc_l2d, opc_l2f, opc_l2i, opc_label, opc_ladd, opc_laload, opc_land, opc_lastore, opc_lcmp, opc_lconst_0, opc_lconst_1, opc_ldc, opc_ldc_w, opc_ldc2_w, opc_ldiv, opc_lload, opc_lload_0, opc_lload_1, opc_lload_2, opc_lload_3, opc_lmul, opc_lneg, opc_lookupswitch, opc_lor, opc_lrem, opc_lreturn, opc_lshl, opc_lshr, opc_lstore, opc_lstore_0, opc_lstore_1, opc_lstore_2, opc_lstore_3, opc_lsub, opc_lushr, opc_lxor, opc_monitorenter, opc_monitorexit, opc_multianewarray, opc_new, opc_newarray, opc_nop, opc_pop, opc_pop2, opc_putfield, opc_putstatic, opc_ret, opc_return, opc_saload, opc_sastore, opc_sipush, opc_swap, opc_tableswitch, opc_try, opc_wide, opc_xxxunusedxxx, opcLengths, opcNames, T_BOOLEAN, T_BYTE, T_CHAR, T_CLASS, T_DOUBLE, T_FLOAT, T_INT, T_LONG, T_SHORT
 
Constructor Summary
EvaluableInterfaceGenerator()
          Degenerate constructor that leaves the specification of the parameters to later calls.
EvaluableInterfaceGenerator(java.lang.Class interfaceName)
           
EvaluableInterfaceGenerator(java.lang.Class sourceInterface, java.lang.String name)
           
EvaluableInterfaceGenerator(java.lang.String interfaceName)
          Creates a new class whose name is created by taking the last element of the interface's class name (that is with the package qualifier removed) and prefixing the result with "Function".
EvaluableInterfaceGenerator(java.lang.String[] args, java.lang.String name)
          Constructor taking an array of Java interface names which are to be implemented by the new class and the name of this new class.
EvaluableInterfaceGenerator(java.lang.String[] args, java.lang.String name, boolean make)
          Constructor taking an array of Java interface names which are to be implemented by the new class and the name of this new class and a flag controlling whether the class is created immediately or deferred awaiting an explicit call to make().
EvaluableInterfaceGenerator(java.lang.String interfaceName, java.io.File f)
          Constructor specifying the name of the Java interface being implemented and the file to which the byte-code should be written for persistent storage.
EvaluableInterfaceGenerator(java.lang.String interfaceName, java.io.File f, boolean make)
          Constructor specifying the name of the Java interface being implemented and the file to which the byte-code should be written for persistent storage and a flag indicating whether to define the class now or wait for an explicit call to to create it.
EvaluableInterfaceGenerator(java.lang.String interfaceName, java.lang.String name)
          Constructor taking the name of the Java interface to be implemented and the name of the new class to be generated.
EvaluableInterfaceGenerator(java.lang.String interfaceName, java.lang.String name, boolean make)
          Constructor taking the name of the Java interface to be implemented, the name of the new class being created and a flag controlling whether we should go ahead and define the class or wait for an explicit call to create it.
 
Method Summary
 jas.CodeAttr addConstructor(Signature sig)
          Add a constructor with the specified "signature" to the class being defined.
 boolean addConstructors()
          Add the default constructors to the class being defined, either copying those inherited from the parent/base class or providing our own which take a Function and Evaluator or just a function.
protected  boolean addDispatchCall(jas.CodeAttr code, java.lang.String methodName, java.lang.String signature, java.lang.String returnClass)
          Method that allows derived classes to change the way the generated methods actually invoke other methods to get things done, having gathered the arguments into an ArgList
 boolean addInterface(java.lang.Class c)
          Add the specified Java interface class to the list of interfaces being implemented by this class.
 int addMethod(java.lang.reflect.Method m)
          Create an entry in the class being defined for the specified Java method, implementing it as a call to the function stored by the object with the arguments passed to this method.
 java.lang.Class addTarget(java.lang.Class c)
           
 java.lang.Class addTarget(java.lang.String name)
          Add the interface class identified (explicitly) by the argument name to the list of interfaces This is stored in the interfaces field and only added to the class definition via the method addInterface(Class) during the make() call.
 int createArgumentList(jas.CodeAttr code, java.lang.Class[] args, java.lang.StringBuffer signature)
          Method that adds the appropriate VM instructions to collect the arguments identified by the array of classes into a FunctionCallArguments list and store it in a local variable for the method being defined identified by the return value.
 int createArgumentList(jas.CodeAttr code, java.lang.Class[] args, java.lang.StringBuffer signature, boolean setSizes)
          Method that adds the appropriate VM instructions to collect the arguments identified by the array of classes into a FunctionCallArguments list and store it in a local variable for the method being defined identified by the return value.
 int createArgumentList(jas.CodeAttr code, java.lang.reflect.Method m, java.lang.StringBuffer signature)
          Method that adds the appropriate VM instructions to collect the arguments in a call to the method m into a FunctionCallArguments list and store it in a local variable for the method being defined identified by the return value.
 int createArgumentList(jas.CodeAttr code, java.lang.reflect.Method m, java.lang.StringBuffer signature, boolean setSizes)
          Method that adds the appropriate VM instructions to collect the arguments in a call to the method m into a FunctionCallArguments list and store it in a local variable for the method being defined identified by the return value.
 java.lang.String derivedClassName(java.lang.String interfaceName)
          Computes the name of the new class based on the name supplied to it, presumably the name of (one of ) the source classes/interfaces, by removing the package name and prefixing the word Function to it.
protected  int getStackSize()
          The number of locations on the stack over and above the number of arguments to the method.
 void init(java.lang.String interfaceName, java.lang.String name, boolean make)
           
 java.util.Vector interfaces()
          Accessor to the interfaces field.
 boolean make()
          Method called to define the contents of the class.
 boolean make(java.lang.Class c)
          Add implementations for the methods specified in the Java interface identified by the argument c.
protected  int numLocalVariables(int numArgs)
          The number of local variables in addition to the number of arguments.
 java.lang.String separator()
          Accessor to the separator field.
 boolean superClassConstructors()
          Accessor for the field userSuperClassConstructors.
 boolean superClassConstructors(boolean v)
          Specification accessor for the field userSuperClassConstructors.
 
Methods inherited from class org.omegahat.Environment.Compile.DynamicCompiler
accessorBody, accessorBody, addConstructor, addField, addField, addField, addField, addField, addField, addFieldAccessors, addFieldAccessors, addFieldAccessors, addInheritedConstructors, addReturn, addReturn, classDef, classDef, className, className, className, className, Debug, Debug, file, file, findClass, findClass, initClassDef, loadCode, mapPrimitive, packageName, packageName, primitiveLoadOp, primitiveToClass, returnPrimitive, returnPrimitive, superClassName, superClassName, warning, write, write, write, write, write
 
Methods inherited from class java.lang.Object
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
 

Field Detail

signaturePrefix

public static java.lang.String signaturePrefix

signatureSuffix

public static java.lang.String signatureSuffix

interfaces

protected java.util.Vector interfaces
A collection of the different interface Classes being implemented by the new class.

separator

protected java.lang.String separator
Separator used when displaying a non-primitive class, used when creating method signatures.

useSuperClassConstructors

protected boolean useSuperClassConstructors
Flag indicating whether the newly defined class should copy the constructors from its parent/base class (true) or not.
Constructor Detail

EvaluableInterfaceGenerator

public EvaluableInterfaceGenerator()
Degenerate constructor that leaves the specification of the parameters to later calls.

EvaluableInterfaceGenerator

public EvaluableInterfaceGenerator(java.lang.String interfaceName,
                                   java.lang.String name)
                            throws java.lang.ClassNotFoundException
Constructor taking the name of the Java interface to be implemented and the name of the new class to be generated.

EvaluableInterfaceGenerator

public EvaluableInterfaceGenerator(java.lang.String interfaceName)
                            throws java.lang.ClassNotFoundException
Creates a new class whose name is created by taking the last element of the interface's class name (that is with the package qualifier removed) and prefixing the result with "Function". Convenience method for discardable classes!

EvaluableInterfaceGenerator

public EvaluableInterfaceGenerator(java.lang.String interfaceName,
                                   java.lang.String name,
                                   boolean make)
                            throws java.lang.ClassNotFoundException
Constructor taking the name of the Java interface to be implemented, the name of the new class being created and a flag controlling whether we should go ahead and define the class or wait for an explicit call to create it.

EvaluableInterfaceGenerator

public EvaluableInterfaceGenerator(java.lang.String interfaceName,
                                   java.io.File f)
                            throws java.lang.ClassNotFoundException
Constructor specifying the name of the Java interface being implemented and the file to which the byte-code should be written for persistent storage.

EvaluableInterfaceGenerator

public EvaluableInterfaceGenerator(java.lang.String interfaceName,
                                   java.io.File f,
                                   boolean make)
                            throws java.lang.ClassNotFoundException
Constructor specifying the name of the Java interface being implemented and the file to which the byte-code should be written for persistent storage and a flag indicating whether to define the class now or wait for an explicit call to to create it.

EvaluableInterfaceGenerator

public EvaluableInterfaceGenerator(java.lang.String[] args,
                                   java.lang.String name)
                            throws java.lang.ClassNotFoundException
Constructor taking an array of Java interface names which are to be implemented by the new class and the name of this new class.

EvaluableInterfaceGenerator

public EvaluableInterfaceGenerator(java.lang.String[] args,
                                   java.lang.String name,
                                   boolean make)
                            throws java.lang.ClassNotFoundException
Constructor taking an array of Java interface names which are to be implemented by the new class and the name of this new class and a flag controlling whether the class is created immediately or deferred awaiting an explicit call to make().

EvaluableInterfaceGenerator

public EvaluableInterfaceGenerator(java.lang.Class interfaceName)

EvaluableInterfaceGenerator

public EvaluableInterfaceGenerator(java.lang.Class sourceInterface,
                                   java.lang.String name)
Method Detail

init

public void init(java.lang.String interfaceName,
                 java.lang.String name,
                 boolean make)
          throws java.lang.ClassNotFoundException

make

public boolean make()
Method called to define the contents of the class.

make

public boolean make(java.lang.Class c)
Add implementations for the methods specified in the Java interface identified by the argument c.

addMethod

public int addMethod(java.lang.reflect.Method m)
Create an entry in the class being defined for the specified Java method, implementing it as a call to the function stored by the object with the arguments passed to this method.

addDispatchCall

protected boolean addDispatchCall(jas.CodeAttr code,
                                  java.lang.String methodName,
                                  java.lang.String signature,
                                  java.lang.String returnClass)
                           throws jas.jasError
Method that allows derived classes to change the way the generated methods actually invoke other methods to get things done, having gathered the arguments into an ArgList

addInterface

public boolean addInterface(java.lang.Class c)
Add the specified Java interface class to the list of interfaces being implemented by this class. This adds it to the byte-code rather than the list of interfaces help in the interfaces field.

addConstructors

public boolean addConstructors()
Add the default constructors to the class being defined, either copying those inherited from the parent/base class or providing our own which take a Function and Evaluator or just a function.

addConstructor

public jas.CodeAttr addConstructor(Signature sig)
Add a constructor with the specified "signature" to the class being defined.

interfaces

public java.util.Vector interfaces()
Accessor to the interfaces field.

derivedClassName

public java.lang.String derivedClassName(java.lang.String interfaceName)
Computes the name of the new class based on the name supplied to it, presumably the name of (one of ) the source classes/interfaces, by removing the package name and prefixing the word Function to it.

addTarget

public java.lang.Class addTarget(java.lang.String name)
                          throws java.lang.ClassNotFoundException
Add the interface class identified (explicitly) by the argument name to the list of interfaces This is stored in the interfaces field and only added to the class definition via the method addInterface(Class) during the make() call.

addTarget

public java.lang.Class addTarget(java.lang.Class c)

separator

public java.lang.String separator()
Accessor to the separator field.

superClassConstructors

public boolean superClassConstructors()
Accessor for the field userSuperClassConstructors.

superClassConstructors

public boolean superClassConstructors(boolean v)
Specification accessor for the field userSuperClassConstructors.

createArgumentList

public int createArgumentList(jas.CodeAttr code,
                              java.lang.reflect.Method m,
                              java.lang.StringBuffer signature)
Method that adds the appropriate VM instructions to collect the arguments in a call to the method m into a FunctionCallArguments list and store it in a local variable for the method being defined identified by the return value. The position is usually the number of arguments + 2.
Parameters:
code - previously initialized code block into which the instructions will be added.
m - the Java method which is being (re)defined.
signature - The StringBuffer is supplied by the caller and is returned with the signature of the method. This avoids iterating over the method's parameters a second time.

createArgumentList

public int createArgumentList(jas.CodeAttr code,
                              java.lang.reflect.Method m,
                              java.lang.StringBuffer signature,
                              boolean setSizes)
Method that adds the appropriate VM instructions to collect the arguments in a call to the method m into a FunctionCallArguments list and store it in a local variable for the method being defined identified by the return value. The position is usually the number of arguments + 2.
Parameters:
code -  
setSizes - flag indicating whether this method should set the stack and local variable size for the method being defined.
See Also:
createArgumentList(jas.CodeAttr, java.lang.reflect.Method, java.lang.StringBuffer)

createArgumentList

public int createArgumentList(jas.CodeAttr code,
                              java.lang.Class[] args,
                              java.lang.StringBuffer signature)
Method that adds the appropriate VM instructions to collect the arguments identified by the array of classes into a FunctionCallArguments list and store it in a local variable for the method being defined identified by the return value. The position is usually the number of arguments + 2.
Parameters:
code - previously initialized instruction set to which the instructions for generating and populating the argument list will be added
args - array of classes identifying the nature and order of the arguments to this method.
signature - buffer which is populated with an signature created from the specified arguments to define the corresponding Java call signature.

createArgumentList

public int createArgumentList(jas.CodeAttr code,
                              java.lang.Class[] args,
                              java.lang.StringBuffer signature,
                              boolean setSizes)
Method that adds the appropriate VM instructions to collect the arguments identified by the array of classes into a FunctionCallArguments list and store it in a local variable for the method being defined identified by the return value. The position is usually the number of arguments + 2.
Parameters:
code - previously initialized instruction set to which the instructions for generating and populating the argument list will be added
args - array of classes identifying the nature and order of the arguments to this method.
signature - buffer which is populated with an signature created from the specified arguments to define the corresponding Java call signature.
setSizes - flag indicating whether this method should take care of establishing the appropriate sizes for the local variables and stack in the Java method being defined based on the number of classes in the args array.

numLocalVariables

protected int numLocalVariables(int numArgs)
The number of local variables in addition to the number of arguments. This method allows the number of local variables to be specified by a derived class. For example, see ForeignReferenceClassGenerator which requires more variables and an increased stack size and number of variables.

getStackSize

protected int getStackSize()
The number of locations on the stack over and above the number of arguments to the method. This allows a derived class (e.g. ForeignReferenceClassGenerator) to specify this as it needs.
See Also:
addDispatchCall.