public final IRubyObject invoke(Ruby runtime, Function function, HeapInvocationBuffer args) { long address = invoker.invokeAddress(function, args); if (address == 0) { return runtime.getNil(); } int len = (int) IO.getStringLength(address); if (len == 0) { return RubyString.newEmptyString(runtime); } byte[] bytes = new byte[len]; IO.getByteArray(address, bytes, 0, len); RubyString s = RubyString.newStringShared(runtime, bytes); s.setTaint(true); return s; }
abstract static class BaseParameterConverter implements IntParameterConverter { static final com.kenai.jffi.MemoryIO IO = com.kenai.jffi.MemoryIO.getInstance(); public boolean isConvertible(ThreadContext context, IRubyObject value) { return true; } }
static final class StringResultConverter implements IntResultConverter { private static final com.kenai.jffi.MemoryIO IO = com.kenai.jffi.MemoryIO.getInstance(); public static final IntResultConverter INSTANCE = new StringResultConverter(); public final IRubyObject fromNative(ThreadContext context, int value) { long address = ((long) value) & PointerResultConverter.ADDRESS_MASK; return FFIUtil.getString(context.getRuntime(), address); } }
private static final class StringInvoker extends BaseInvoker { private static final com.kenai.jffi.MemoryIO IO = com.kenai.jffi.MemoryIO.getInstance(); public StringInvoker(Function function, ParameterMarshaller[] marshallers) { super(function, marshallers); } public final PyObject invoke(PyObject[] args) { return Util.newString(jffiInvoker.invokeAddress(jffiFunction, convertArguments(args))); } }
/** * Invokes the native function with a native struct return value. Returns a FFI::Struct instance * to ruby. */ private static final class StructByValueInvoker extends BaseInvoker { private static final com.kenai.jffi.MemoryIO IO = com.kenai.jffi.MemoryIO.getInstance(); private final StructByValue info; public StructByValueInvoker(StructByValue info) { this.info = info; } public final IRubyObject invoke(Ruby runtime, Function function, HeapInvocationBuffer args) { return info.newStruct(runtime, invoker.invokeStruct(function, args), 0); } }
/** * Invokes the native function with a callback/function pointer return value. Returns a {@link * Invoker} to ruby. */ private static final class CallbackInvoker extends BaseInvoker { private static final com.kenai.jffi.MemoryIO IO = com.kenai.jffi.MemoryIO.getInstance(); private final Type returnType; private final Type[] parameterTypes; public CallbackInvoker(CallbackInfo cbInfo) { this.returnType = cbInfo.getReturnType(); this.parameterTypes = cbInfo.getParameterTypes(); } public final IRubyObject invoke(Ruby runtime, Function function, HeapInvocationBuffer args) { long address = invoker.invokeAddress(function, args); if (address == 0) { return runtime.getNil(); } return new JFFIInvoker(runtime, address, returnType, parameterTypes); } }
/** * Invokes the native function with a native string return value. Returns a {@link RubyString} to * ruby. */ private static final class StringInvoker extends BaseInvoker { private static final com.kenai.jffi.MemoryIO IO = com.kenai.jffi.MemoryIO.getInstance(); public final IRubyObject invoke(Ruby runtime, Function function, HeapInvocationBuffer args) { long address = invoker.invokeAddress(function, args); if (address == 0) { return runtime.getNil(); } int len = (int) IO.getStringLength(address); if (len == 0) { return RubyString.newEmptyString(runtime); } byte[] bytes = new byte[len]; IO.getByteArray(address, bytes, 0, len); RubyString s = RubyString.newStringShared(runtime, bytes); s.setTaint(true); return s; } public static final FunctionInvoker INSTANCE = new StringInvoker(); }