【问题标题】:Simple and efficient distribution of C++/Boost source code (amalgamation)简单高效的C++/Boost源码分发(合并)
【发布时间】:2011-02-22 00:32:16
【问题描述】:

我的工作主要包括工程分析,但我发现自己越来越频繁地在同事之间分发代码。一个很大的痛苦是不是每个用户都精通编译源代码的复杂性,而且我无法分发可执行文件。

我一直在使用 Boost 使用 C++,但问题是我无法要求每个网络的每个系统管理员都安装这些库。相反,我想分发单个源文件(或尽可能少),以便用户可以g++ source.c -o program

所以,问题是:您能否打包 Boost 库与您的代码,并最终得到一个文件?我说的是“仅标题”或“仅模板”的 Boost 库。

作为灵感,请查看SQliteLemon Parser Generator的分布;作者将这些东西合并到一个易于编译的源文件中。

谢谢。

编辑

related question in SO 用于 Windows 环境。我在 Linux 中工作。

【问题讨论】:

  • 你想沿着这条路走多远?他们可能没有安装的其他库呢?您可能想查看某种包管理器或自动编译机制(可能是 shar 存档?)。

标签: c++ boost software-distribution amalgamation


【解决方案1】:

如果您使用的是 Debian 衍生的各种 Linux,那么就不应该出现这样的问题:让打包系统和策略手册来完成工作。只需明确说明 libboost-dev 或任何软件包是您的代码的构建依赖项,需要事先安装,然后 /usr/include/boost 应该就在您的代码期望找到它的位置。如果您使用的是比发行版更新的 boost 版本,那么可能值得弄清楚如何自己打包它并在现有的打包/依赖框架内工作,而不是重新发明另一个。

我对基于 .rpm 的发行版不够熟悉,无法评论那里的工作方式。但是知道我可以轻松地准确设置我需要的构建环境,对我来说,这是基于 Debian 的开发相对于 Windows 的最大优势之一。

【讨论】:

    【解决方案2】:

    在您的代码上运行预处理器并保存输出。如果您从一个包含一堆包含的 main.cpp 开始,您最终会得到一个包含所有包含的文件。如果您有多个 cpp 文件,则必须将它们连接在一起然后运行连接文件上的预处理器,只要您没有任何重复的全局符号名称,这应该可以工作。

    对于更便携的方法,执行 sqlite 的操作并编写您自己的脚本,将您创建的文件组合并连接在一起+boost,而不是让系统包含。在 sqlite 代码中查看 mksqlite3c.tcl
    http://www2.sqlite.org/src/finfo?name=tool/mksqlite3c.tcl

    【讨论】:

    • 没错,但我正在回答他提出的问题,即如何将其制作为一个文件。
    【解决方案3】:

    boost 附带了一个名为bcp 的实用程序,它可以扫描您的源并从 boost 源中提取任何使用的 boost 头文件。我已经设置了一个脚本,将这个提取到我们的源代码树中,这样我们就可以将我们需要的源代码与我们的代码一起打包。它还将复制我们使用的几个boost库的boost源文件,这些库没有头文件,然后直接编译到我们的应用程序中。

    这是一次完成,然后任何使用该代码的人甚至不需要知道它依赖于 boost。这是我们使用的。如果尚未构建 bjam 和 bcp,它也会构建它们。

    #!/bin/sh
    BOOST_SRC=.../boost_1_43_0
    DEST_DIR=../src/boost
    TOOLSET=
    if ( test `uname` = "Darwin") then
        TOOLSET="--toolset=darwin"
    fi
    
    # make bcp if necessary
    if ( ! test -x $BOOST_SRC/dist/bin/bcp ) then
        if ( test -x $BOOST_SRC/tools/jam/*/bin.*/bjam ) then
            BJAM=$BOOST_SRC/tools/jam/*/bin.*/bjam
        else
            echo "### Building bjam"
            pushd $BOOST_SRC/tools/jam
            ./build_dist.sh
            popd
            if ( test -x $BOOST_SRC/tools/jam/*/bin.*/bjam ) then
                BJAM=$BOOST_SRC/tools/jam/*/bin.*/bjam
            fi
    
        fi
        echo "BJAM: $BJAM"
        pushd $BOOST_SRC/tools/bcp
        echo "### Building bcp"
        echo "$BJAM $TOOLSET"
        $BJAM $TOOLSET
        if [ $? == "0" ]; then
            exit 1;
        fi
        popd
    fi
    
    if ( ! test -x $BOOST_SRC/dist/bin/bcp) then
        echo "### Couldn't find bpc"
        exit 1;
    fi
    
    mkdir -p $DEST_DIR
    
    echo "### Copying boost source"
    MAKEFILEAM=$DEST_DIR/libs/Makefile.am
    rm $MAKEFILEAM
    # Signals
    # copy source libraries
    mkdir -p $DEST_DIR/libs/signals/src
    cp $BOOST_SRC/libs/signals/src/* $DEST_DIR/libs/signals/src/.
    echo -n "boost_sources += " >> $MAKEFILEAM
    for f in `ls $DEST_DIR/libs/signals/src | fgrep .cpp`; do
        echo -n "boost/libs/signals/src/$f " >> $MAKEFILEAM
    done
    echo >> $MAKEFILEAM
    
    echo "### Extracting boost includes"
    $BOOST_SRC/dist/bin/bcp --scan --boost=$BOOST_SRC ../src/*/*.[Ch] ../src/boost/libs/*/src/*.cpp ../src/smart_assert/smart_assert/priv/fwd/*.hpp $DEST_DIR
    if [ $? != "0" ]; then
        echo "### bcp failed"
        rm -rf $DEST_DIR
        exit 1;
    fi
    

    【讨论】:

    • 谢谢。这与我最终要做的非常接近。
    【解决方案4】:

    您是否考虑过为 SCons 这样的构建系统编写构建脚本?
    您可以编写一个 python 脚本来下载 boost,解压缩它并编译所需的文件(如果需要,您甚至可以运行 bjam)并编译您自己的代码。
    您的同事需要的唯一依赖项是 Python 和 SCons。

    【讨论】:

      【解决方案5】:

      为什么不直接将所有必要的文件签入到 SVN,然后将存储库的 URL 发送给您的同事?然后他们可以随时查看代码,随时执行“svn up”更新到最新版本等。

      【讨论】:

      • 这对你和我都有效,但对我的一些同事来说,这需要比他们愿意/有时间忍受的更复杂。
      • 您可以将复杂性封装在脚本或 GUI 前端中。这实际上只是一个“svn co”(或“svn up”)命令的问题,然后是 configure;make 或其他。只需一点点工作,它就可以通过双击一个图标来启动。
      猜你喜欢
      • 2014-12-24
      • 2011-07-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多