是否可以拆分 SWIG 模块进行编译,但在链接时重新加入它? [英] Is it possible to split a SWIG module for compilation, but rejoin it when linking?

查看:28
本文介绍了是否可以拆分 SWIG 模块进行编译,但在链接时重新加入它?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

大约两年前,当我第一次实现我们的 SWIG 绑定时,我遇到了这个问题.一旦我们暴露了大量代码,我们就会发现 SWIG 会输出如此大的 C++ 文件,编译器无法处理它们.我能解决这个问题的唯一方法是将接口拆分为多个模块并分别编译.

这有几个缺点:

• 每个模块必须了解其他模块中的依赖关系.我有一个脚本来生成处理这方面事情的接口文件,但它增加了额外的复杂性.

• 每个附加模块都会增加动态链接器加载代码所需的时间.我添加了一个导入所有子模块的 init.py 文件,这样代码被拆分的事实对用户来说是透明的,但总是可见的是加载时间很长.>

我目前正在审查我们的构建脚本/构建过程,我想看看我是否能找到比我现在更好的解决方案.理想情况下,我有一个包含所有包装器代码的共享库.

有谁知道我如何使用 SWIG 实现这一目标?我已经看到一些用 Ruby 为特定项目编写的自定义代码,其中对输出进行了后处理以使这成为可能,但是当我查看 Python 包装器的可行性时,它看起来并不那么容易.

解决方案

我刚刚对 TCL 库做了等效的 hack:我使用了几个 SWIG 模块,生成了几个 .cpp 文件,这些文件在几个 .o 文件中编译,但全部编译由单个 TCL加载"命令加载的单个 .so 文件.

想法是创建一个顶层swig模块(Top),调用所有子模块(Sub1和Sub2)的初始化函数:

%module Top%头%{外部C"{SWIGEXPORT int Sub1_Init(Tcl_Interp *);SWIGEXPORT int Sub2_Init(Tcl_Interp *);}%}%在里面 %{if (Sub1_Init(interp) != TCL_OK) {return TCL_ERROR;}if (Sub2_Init(interp) != TCL_OK) {return TCL_ERROR;}%}

子模块文件没有什么特别之处.我最终得到文件 Top.so,我使用命令load ./Top.so"从 TCL 加载

我不知道 python 但很可能是相似的.不过,您可能需要了解 Python 扩展是如何加载的.

I hit this issue about two years ago when I first implemented our SWIG bindings. As soon as we exposed a large amount of code we got to the point where SWIG would output C++ files so large the compiler could not handle them. The only way I could get around the issue was to split up the interfaces into multiple modules and to compile them separately.

This has several downsides:

• Each module must know about dependencies in other modules. I have a script to generate the interface files which handles this side of things, but it adds extra complexity.

• Each additional module increases the time that the dynamic linker requires to load in the code. I have added an init.py file that imports all the submodules, so that the fact that the code is split up is transparent to the user, but what is always visible is the long load times.

I'm currently reviewing our build scripts / build process and I wanted to see if I could find a solution to this issue that was better than what I have now. Ideally, I'd have one shared library containing all the wrapper code.

Does anyone know how I can acheive this with SWIG? I've seen some custom code written in Ruby for a specific project, where the output is post-processed to make this possible, but when I looked at the feasibility for Python wrappers it does not look so easy.

解决方案

I just did equivalent hack for TCL library: I use several SWIG modules, generating several .cpp files that are compiled in several .o files but compile them all in a single .so file that is loaded by a single TCL "load" command.

The idea is to creates a top swig module (Top) that calls initialization functions of all sub-modules (Sub1 and Sub2):

%module Top
%header %{
  extern "C" {
    SWIGEXPORT int Sub1_Init(Tcl_Interp *);
    SWIGEXPORT int Sub2_Init(Tcl_Interp *);
  }
%}
%init %{
    if (Sub1_Init(interp) != TCL_OK) {return TCL_ERROR;}
    if (Sub2_Init(interp) != TCL_OK) {return TCL_ERROR;}
%}

There's nothing special in the submodules files. I end up with file Top.so that I load from TCL with command "load ./Top.so"

I don't know python but's likely to be similar. You may need to understand how the python extensions are loaded, though.

这篇关于是否可以拆分 SWIG 模块进行编译,但在链接时重新加入它?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆