具有多个C和C ++源文件的mkoctfile

时间:2019-01-14 22:58:03

标签: c++ c compilation linker octave

我无法让 mkoctfile 成功创建一个 oct 文件,该文件是我的某些 C ++ 函数的包装器(例如< code> void my_fun(double *,double))。特别是我的问题是由于包装代码 my_fun_wrap.cpp 需要包含 库(仅提供C ++)而引起的。 标头(请参见此处),但是 my_fun 的原始代码也使用 C 中的源代码。例如

  // my_fun_wrapper.cpp

#include 
#include“ custom_functions_libc.h”

DEFUN_DLD(my_fun_wrapper,args,“带延迟的EI MF网络模型A(Brunel,JCN 2000)”){

//输入参数
NDArray xvar = args(0).array_value();
双x = xvar(0);

//输出参数
双dy [4];
dim_vector dv(4,1);
NDArray dxvars(dv);

//调用我的C函数,该函数还在lib文件custom_functions_libc.c中包含代码
my_fun(dy,x);

//然后将输出值分配给NDArray
for(int i = 0; i <4; i ++)dxvars(i)= dy [i];

//根据八度音阶准则将输出强制转换为octave_value
返回octave_value(dxvars);
}
 

然后假设我的 custom_functions_libc.h custom_functions_libc.c 文件位于文件夹 / my_libs 中。理想情况下,从Octave命令行,我可以通过以下方式进行编译:

  mkoctfile -g -v -O -I <路径文件夹> / my_libs <路径文件夹> /my_libs/custom_functions_libc.c my_fun_wrapper.cpp-输出my_fun_wrapper -lm -lgsl -lgslcblas
 

这实际上会根据需要生成 my_fun_wrapper.oct 。然后我可以从某些 octave 代码(例如

)中调用后者
  ...
...
xx = [0.,2.5,1.];
yy = [1e-5,0.1,2];

dxv = test_my_function(xx,yy);


函数dy = test_my_function(xx,yy)
    xx + = yy ** 2;
    dy = my_fun_wrapper(xx);
终端功能
 

事实证明,以上代码将退出,并在 test_my_function 中显示错误,表示在 my_fun_wrapper 中未识别符号 Zmy_fundd 。收到此类错误后,我怀疑链接过程中出现了问题。但是奇怪的是,编译器没有产生任何错误,正如我所说。但是,仔细检查编译器的详细输出后发现, mkoctfile 正在根据文件的扩展名在不同文件之间自动更改编译器。因此 my_fun_wrapper.cpp g ++ -std = gnu ++ 11 编译,而 custom_function_libc.c gcc -std =编译gnu11 ,以及与 my_fun_wrapper.o 链接时,此编译过程产生的 custom_function_libc.o 文件不匹配。

上面的例子非常简单。实际上,就我而言, custom_function_libc 包括更多自定义 C 库。到目前为止,一种解决方法是将这些库的 .c 源文件克隆到 .cpp 文件中。但是我不太喜欢这种解决方案。

我最终如何才能安全地混合 C ++ C 代码并通过 mkoctfile 成功地进行编译? octave 手册建议在 extern C 规范之前添加(请参阅此处),恐怕我不太熟悉。这是最好的方法吗?您能否建议我一个潜在的替代解决方案?

1 个答案:

答案 0 :(得分:1)

So apparently the easiest solution, according to my above post is to correct the wrapper by the following preprocessor directives:

// my_fun_wrapper.cpp

#include <octave/oct.h>

// ADDED code to include the C source code
#ifdef __cplusplus
extern "C"
{
#endif
// END ADDITION
#include "custom_functions_libc.h"
// ADDED code to include the C source code
#ifdef __cplusplus
}  /* end extern "C" */
#endif
// END ADDITION

...
...

This will compile and link fine.