classFile.generateMethodInfoHeader(binding);
int methodAttributeOffset = classFile.contentsOffset;
int attributeNumber = classFile.generateMethodInfoAttribute(binding, false, AstUtil.getAjSyntheticAttribute());
int codeAttributeOffset = classFile.contentsOffset;
classFile.generateCodeAttributeHeader();
CodeStream codeStream = classFile.codeStream;
codeStream.reset(this, classFile);
// push the closure
int nargs = binding.parameters.length;
int closureIndex = 0;
for (int i=0; i < nargs-1; i++) {
closureIndex += AstUtil.slotsNeeded(binding.parameters[i]);
}
codeStream.loadObject(closureIndex);
// build the Object[]
codeStream.generateInlinedValue(nargs-1);
codeStream.newArray(
new ArrayBinding(
classScope.getType(TypeBinding.JAVA_LANG_OBJECT,
TypeBinding.JAVA_LANG_OBJECT.length),
1,
classScope.environment()));
int index = 0;
for (int i=0; i < nargs-1; i++) {
TypeBinding type = binding.parameters[i];
codeStream.dup();
codeStream.generateInlinedValue(i);
codeStream.load(type, index);
index += AstUtil.slotsNeeded(type);
if (type.isBaseType()) {
codeStream.invokestatic(AjTypeConstants.getConversionMethodToObject(classScope, type));
}
codeStream.aastore();
}
// call run
ReferenceBinding closureType = (ReferenceBinding)binding.parameters[nargs-1];
MethodBinding runMethod = closureType.getMethods("run".toCharArray())[0];
codeStream.invokevirtual(runMethod);
TypeBinding returnType = binding.returnType;
if (returnType.isBaseType()) {
codeStream.invokestatic(AjTypeConstants.getConversionMethodFromObject(classScope, returnType));
} else {
codeStream.checkcast(returnType);
}
AstUtil.generateReturn(returnType, codeStream);
classFile.completeCodeAttribute(codeAttributeOffset);
attributeNumber++;