SWIGJava:如何调用带有void * out参数的函数?

问题描述

背景

我正在使用C ++代码库开发适用于Android的实时通信应用程序。我使用SWIG生成一个JNI桥,以从Java访问本机代码。为了跟踪正在进行的呼叫,将void*用作句柄(指向包含有关正在进行的呼叫的信息的地址)。以下函数头是如何使用它的示例:

void initiateCall(void** callHandleRef);

void closeCall(void* callHandle);

initateCall接受void**,分配一个结构并将其地址(作为void *)写入callHandleRef。它用作“输出”参数,因为您将其作为参数传递并期望将某些内容写入该参数。调用closeCall时,将传递原始指针,从而使C ++库可以访问与该特定调用关联的数据。

问题描述

我想使用SWIG从Java调用initiateCallcloseCall生成执行此操作所需的JNI代码。然而。 SWIG分别生成类型“ SWIGTYPE_p_p_void”和“ SWIGTYPE_p_void”,而我无法以上述方式使用它们。如何设置我的SWIG接口文件以允许我执行此操作?

解决方法

here所示,Flexo对这个问题的评论对我有用。这是我的解决方案,或多或少地从他们的答案中粘贴。

C ++标头(call.h):

typedef void* CALL_HANDLE;

int initiateCall(const char* name,CALL_HANDLE* handle);
int closeCall(CALL_HANDLE handle);

SWIG接口(call.i):

%module bridge

%include <cpointer.i>

%pointer_class(CALL_HANDLE,inst_ptr);
%javamethodmodifiers initiateCall "private";
%pragma(java) modulecode=%{
  public static SWIGTYPE_p_void initiateCall(String name) {
      inst_ptr ptr = new inst_ptr();
      final int err = initiateCall(name,ptr.cast());
      if (0 != err) {
          // Throw error or something like that
      }
      return ptr.value();
  }
%}

%include "include/call.h"

extern int initiateCall(const char* name,CALL_HANDLE* handle);
extern int closeCall(CALL_HANDLE handle);

主要活动(MainActivity.kt):

class MainActivity : AppCompatActivity() {
    private lateinit var callHandle: SWIGTYPE_p_void

    fun call(name: String) {
        callHandle = bridge.initiateCall(name)
    }

    fun hangup() {
        bridge.closeCall(callHandle)
    }
}