package org.jruby.ext.ffi.jffi;
import com.kenai.jffi.Closure;
import org.jruby.Ruby;
import org.jruby.RubyClass;
import org.jruby.RubyModule;
import org.jruby.anno.JRubyClass;
import org.jruby.ext.ffi.AbstractInvoker;
import org.jruby.ext.ffi.CallbackInfo;
import org.jruby.ext.ffi.MemoryIO;
import org.jruby.internal.runtime.methods.DynamicMethod;
@JRubyClass(name = "FFI::Callback", parent = "FFI::Pointer")
class NativeCallbackPointer extends AbstractInvoker {
final CallbackInfo cbInfo;
final NativeFunctionInfo closureInfo;
NativeCallbackPointer(Ruby runtime, RubyClass klass, Closure.Handle handle, CallbackInfo cbInfo, NativeFunctionInfo closureInfo) {
super(runtime, klass,
cbInfo.getParameterTypes().length, new CallbackMemoryIO(runtime, handle));
this.cbInfo = cbInfo;
this.closureInfo = closureInfo;
}
void dispose() {
MemoryIO mem = getMemoryIO();
if (mem instanceof CallbackMemoryIO) {
((CallbackMemoryIO) mem).free();
}
}
@Override
public DynamicMethod createDynamicMethod(RubyModule module) {
com.kenai.jffi.Function function = new com.kenai.jffi.Function(getMemoryIO().address(),
closureInfo.jffiReturnType, closureInfo.jffiParameterTypes);
return MethodFactory.createDynamicMethod(getRuntime(), module, function,
closureInfo.returnType, closureInfo.parameterTypes, closureInfo.convention, getRuntime().getNil(), false);
}
}