use of lucee.transformer.bytecode.ConstrBytecodeContext in project Lucee by lucee.
the class ComponentUtil method createMethod.
private static int createMethod(ConstrBytecodeContext constr, java.util.List<LitString> keys, ClassWriter cw, String className, Object member, int max, boolean writeLog, boolean suppressWSbeforeArg, boolean output, boolean returnValue) throws PageException {
boolean hasOptionalArgs = false;
if (member instanceof UDF) {
UDF udf = (UDF) member;
FunctionArgument[] args = udf.getFunctionArguments();
Type[] types = new Type[max < 0 ? args.length : max];
for (int y = 0; y < types.length; y++) {
types[y] = toType(args[y].getTypeAsString(), true);
if (!args[y].isRequired())
hasOptionalArgs = true;
}
Type rtnType = toType(udf.getReturnTypeAsString(), true);
Method method = new Method(udf.getFunctionName(), rtnType, types);
GeneratorAdapter adapter = new GeneratorAdapter(Opcodes.ACC_PUBLIC + Opcodes.ACC_FINAL, method, null, null, cw);
BytecodeContext bc = new BytecodeContext(null, constr, getPage(constr), keys, cw, className, adapter, method, writeLog, suppressWSbeforeArg, output, returnValue);
Label start = adapter.newLabel();
adapter.visitLabel(start);
// ComponentController.invoke(name, args);
// name
adapter.push(udf.getFunctionName());
// args
ArrayVisitor av = new ArrayVisitor();
av.visitBegin(adapter, Types.OBJECT, types.length);
for (int y = 0; y < types.length; y++) {
av.visitBeginItem(adapter, y);
adapter.loadArg(y);
av.visitEndItem(bc.getAdapter());
}
av.visitEnd();
adapter.invokeStatic(Types.COMPONENT_CONTROLLER, INVOKE);
adapter.checkCast(rtnType);
// ASMConstants.NULL(adapter);
adapter.returnValue();
Label end = adapter.newLabel();
adapter.visitLabel(end);
for (int y = 0; y < types.length; y++) {
adapter.visitLocalVariable(args[y].getName().getString(), types[y].getDescriptor(), null, start, end, y + 1);
}
adapter.endMethod();
if (hasOptionalArgs) {
if (max == -1)
max = args.length - 1;
else
max--;
return max;
}
}
return -1;
}
use of lucee.transformer.bytecode.ConstrBytecodeContext in project Lucee by lucee.
the class ComponentUtil method getComponentJavaAccess.
// private static final Method INVOKE_PROPERTY = new Method("invoke",Types.OBJECT,new Type[]{Types.STRING,Types.OBJECT_ARRAY});
/**
* generate a ComponentJavaAccess (CJA) class from a component
* a CJA is a dynamic genarted java class that has all method defined inside a component as java methods.
*
* This is used to generated server side Webservices.
* @param component
* @param isNew
* @return
* @throws PageException
*/
public static Class getComponentJavaAccess(PageContext pc, Component component, RefBoolean isNew, boolean create, boolean writeLog, boolean suppressWSbeforeArg, boolean output, boolean returnValue) throws PageException {
isNew.setValue(false);
String classNameOriginal = component.getPageSource().getClassName();
String className = getClassname(component, null).concat("_wrap");
String real = className.replace('.', '/');
String realOriginal = classNameOriginal.replace('.', '/');
Mapping mapping = component.getPageSource().getMapping();
PhysicalClassLoader cl = null;
try {
cl = (PhysicalClassLoader) ((PageContextImpl) pc).getRPCClassLoader(false);
} catch (IOException e) {
throw Caster.toPageException(e);
}
Resource classFile = cl.getDirectory().getRealResource(real.concat(".class"));
Resource classFileOriginal = mapping.getClassRootDirectory().getRealResource(realOriginal.concat(".class"));
// check last Mod
if (classFile.lastModified() >= classFileOriginal.lastModified()) {
try {
Class clazz = cl.loadClass(className);
if (clazz != null && !hasChangesOfChildren(classFile.lastModified(), clazz))
return registerTypeMapping(clazz);
} catch (Throwable t) {
ExceptionUtil.rethrowIfNecessary(t);
}
}
if (!create)
return null;
isNew.setValue(true);
// print.out("new");
// CREATE CLASS
ClassWriter cw = ASMUtil.getClassWriter();
cw.visit(Opcodes.V1_6, Opcodes.ACC_PUBLIC, real, null, "java/lang/Object", null);
// GeneratorAdapter ga = new GeneratorAdapter(Opcodes.ACC_PUBLIC,Page.STATIC_CONSTRUCTOR,null,null,cw);
// StaticConstrBytecodeContext statConstr = null;//new BytecodeContext(null,null,null,cw,real,ga,Page.STATIC_CONSTRUCTOR);
// /ga = new GeneratorAdapter(Opcodes.ACC_PUBLIC,Page.CONSTRUCTOR,null,null,cw);
// new BytecodeContext(null,null,null,cw,real,ga,Page.CONSTRUCTOR);
ConstrBytecodeContext constr = null;
// field component
// FieldVisitor fv = cw.visitField(Opcodes.ACC_PRIVATE, "c", "Llucee/runtime/ComponentImpl;", null, null);
// fv.visitEnd();
java.util.List<LitString> _keys = new ArrayList<LitString>();
// remote methods
Collection.Key[] keys = component.keys(Component.ACCESS_REMOTE);
int max;
for (int i = 0; i < keys.length; i++) {
max = -1;
while ((max = createMethod(constr, _keys, cw, real, component.get(keys[i]), max, writeLog, suppressWSbeforeArg, output, returnValue)) != -1) {
// for overload remove this
break;
}
}
// Constructor
GeneratorAdapter adapter = new GeneratorAdapter(Opcodes.ACC_PUBLIC, CONSTRUCTOR_OBJECT, null, null, cw);
adapter.loadThis();
adapter.invokeConstructor(Types.OBJECT, CONSTRUCTOR_OBJECT);
lucee.transformer.bytecode.Page.registerFields(new BytecodeContext(null, constr, getPage(constr), _keys, cw, real, adapter, CONSTRUCTOR_OBJECT, writeLog, suppressWSbeforeArg, output, returnValue), _keys);
adapter.returnValue();
adapter.endMethod();
cw.visitEnd();
byte[] barr = cw.toByteArray();
try {
ResourceUtil.touch(classFile);
IOUtil.copy(new ByteArrayInputStream(barr), classFile, true);
cl = (PhysicalClassLoader) ((PageContextImpl) pc).getRPCClassLoader(true);
return registerTypeMapping(cl.loadClass(className, barr));
} catch (Throwable t) {
ExceptionUtil.rethrowIfNecessary(t);
throw Caster.toPageException(t);
}
}
use of lucee.transformer.bytecode.ConstrBytecodeContext in project Lucee by lucee.
the class Function method loadUDFProperties.
public final void loadUDFProperties(BytecodeContext bc, int valueIndex, int arrayIndex, int type) {
ConstrBytecodeContext constr = bc.getConstructor();
// GeneratorAdapter cga = constr.getAdapter();
GeneratorAdapter ga = bc.getAdapter();
// store to construction method
constr.addUDFProperty(this, arrayIndex, valueIndex, type);
/*cga.visitVarInsn(ALOAD, 0);
cga.visitFieldInsn(GETFIELD, bc.getClassName(), "udfs", Types.UDF_PROPERTIES_ARRAY.toString());
cga.push(arrayIndex);
createUDFProperties(constr,valueIndex,type);
cga.visitInsn(AASTORE);*/
// load in execution method
ga.visitVarInsn(ALOAD, 0);
ga.visitFieldInsn(GETFIELD, bc.getClassName(), "udfs", Types.UDF_PROPERTIES_ARRAY.toString());
ga.push(arrayIndex);
ga.visitInsn(AALOAD);
}
Aggregations