Boost 了解bjam&x27;s目标,以及如何指定新的目标?

Boost 了解bjam&x27;s目标,以及如何指定新的目标?,boost,makefile,boost-python,bjam,boost-build,Boost,Makefile,Boost Python,Bjam,Boost Build,我在理解如何使用bjam指定和调用目标时遇到问题。我的意思是,我希望为bjam提供与构建过程的不同方面相对应的要构建的命令行目标(实际上是从一个Makefile),而不仅仅是运行整个过程 例如,现在当我输入'bjam'时,它会启动并构建一个python扩展,运行一个单元测试文件,还创建一个单独的'main'可执行文件。我有执行每个步骤的自定义规则,我的Jamfile只是按顺序列出它们: project-name = example ; sources = $(project-name).c

我在理解如何使用bjam指定和调用目标时遇到问题。我的意思是,我希望为bjam提供与构建过程的不同方面相对应的要构建的命令行目标(实际上是从一个Makefile),而不仅仅是运行整个过程

例如,现在当我输入'bjam'时,它会启动并构建一个python扩展,运行一个单元测试文件,还创建一个单独的'main'可执行文件。我有执行每个步骤的自定义规则,我的Jamfile只是按顺序列出它们:

project-name = example ;

sources =
  $(project-name).cpp
  $(project-name)_ext.cpp
  ;

build-ext $(project-name) : $(sources) ;

build-main $(project-name) ;
在我的Jamroot(上一个目录)中定义了这些规则,下面是不完整的文件:

# A rule to simplify declaration of extension tests:
rule run-test ( test-name : sources + )
{
    import testing ;
    testing.make-test run-pyd : $(sources) : : $(test-name) ;
}

# A rule to further simply declaration of extension tests:
rule run-ext-test ( project-name )
{
  run-test $(project-name) : $(project-name)_ext test_$(project-name)_ext.py ;
}

# A rule to simplify copying of the extension and Boost.Python libraries to the current directory
rule convenient-copy ( project-name )
{
  install convenient_copy
    : $(project-name)_ext
    : <install-dependencies>on <install-type>SHARED_LIB <install-type>PYTHON_EXTENSION
      <location>.
    ;
}

rule build-ext ( project-name : sources + )
{
  python-extension $(project-name)_ext : $(sources) : ;

  # copy the extension and Boost.Python libraries to the current directory
  convenient-copy $(project-name) ;

  # run extension tests
  run-ext-test $(project-name) ;
}

rule build-main ( project-name : other-sources * )
{
  obj $(project-name).o : $(project-name).cpp ;
  exe main_$(project-name) : main_$(project-name).cpp $(project-name).o $(other-sources) ;
  install main : main_$(project-name) : <location>. ;
}
这确实在Jamfile目录中创建了二进制文件

main
目标来自哪里?我没有定义它

另一个奇怪的问题是:

$ bjam example_ext
...patience...
...patience...
...found 2834 targets...
...updating 3 targets...
gcc.compile.c++ bin/gcc-4.6/debug/example.o
gcc.compile.c++ bin/gcc-4.6/debug/example_ext.o
gcc.link.dll bin/gcc-4.6/debug/example_ext.so
...updated 3 targets...
^^^创建了example_ext.so,但没有将其复制到Jamfile位置

$ bjam example_ext.so
notice: could not find main target example_ext.so
notice: assuming it is a name of file to create.
...patience...
...patience...
...found 2836 targets...
...updating 4 targets...
gcc.compile.c++ bin/gcc-4.6/debug/example.o
gcc.compile.c++ bin/gcc-4.6/debug/example_ext.o
gcc.link.dll bin/gcc-4.6/debug/example_ext.so
common.copy example_ext.so
...updated 4 targets...
^^^创建了.so文件并对其进行了复制,但没有调用方便复制来引入libboost_python.so文件

我真的不明白这里发生了什么。bjam文档确实给我带来了严重的问题。它详细描述了目标,但在规则上下文中,而不是在从命令行调用bjam的上下文中。我确实遇到过一些关于伪目标和“生成”的提及,但对于我认为应该是一个简单的用例来说,它似乎太复杂了。还提到了“绑定”机制,但文档中提到了
=$(BINDRULE[1])=
,这对我来说毫无意义

我还遇到了别名,
NOTFILE
explicit
,但我不确定自己的思路是否正确,也无法做出任何结论


有没有关于如何在bjam中创建自定义目标的好例子?或者我只是想以不希望的方式使用bjam?

不带参数的调用bjam会生成所有内容,因为没有任何目标标记为
explicit
,除非明确请求,否则可以使用它来阻止某些目标生成

bjam build main
失败,因为
build main
不是要生成的目标或文件的名称;它是可以使用不同参数调用的规则(函数)的名称,每个调用声明不同的目标集

bjam main\u示例
生成使用以下命令声明的目标:

exe main_$(project-name) : main_$(project-name).cpp $(project-name).o $(other-sources) ;
python-extension $(project-name)_ext : $(sources) : ;
它自然不包含下一行声明的
install
目标

bjam main
生成
main\u示例并安装它,因为
main
是其
install
目标的名称,声明为:
install main:main\u$(项目名称):

请注意,如果在jamfile中多次调用
build main
,则每次bjam调用都会出现
error:No-best alternative for./main
,因此最好将安装目标的名称重命名为类似
install\u main$(项目名称)
的名称,以防止名称冲突。然后,
bjam install\u main\u示例
将构建并安装
main\u示例

bjam example\u ext
生成使用以下命令声明的目标:

exe main_$(project-name) : main_$(project-name).cpp $(project-name).o $(other-sources) ;
python-extension $(project-name)_ext : $(sources) : ;
并且不再像bjam main_示例那样安装

bjam example_ext.so
作为
example_ext.so
实际上是一个正在创建的文件名(当然是在给定的平台下),因此所有生成名为
example_ext.so
的文件的目标都将通过该调用生成。这就是为什么不是所有被指示安装的
方便复制
文件都是通过
bjam example\u ext.so
调用安装的。这里我想澄清一点:“没有调用方便复制”不是一个非常准确的术语<代码>方便复制
是一个规则的名称,而不是目标,使用上面所写的代码,无论bjam调用参数如何,该规则始终会被调用。调用时所做的一切就是声明一个名为
conventive\u copy
(请注意下划线)的目标,这反过来会(隐式地)声明几个文件目标(用于安装),例如example\u ext.so、libboost\u python.so和其他与
共享库python\u扩展名
匹配的依赖项。当调用
便利复制
规则时,它实际上并不构建任何东西,它只是声明一些目标。实际生成的内容将在稍后的阶段决定,并且该决定取决于bjam调用参数

bjam-conventive\u-copy
将构建example\u ext.so并将其与其依赖项一起正确安装,但它遇到与
main
install-target相同的问题:如果多次调用
conventive-copy
,它将崩溃。将名称从
conventive\u copy
更改为
install\u$(项目名称)\u ext
将解决此问题,然后使用
bjam install\u example\u ext
调用安装

最后,如果希望目标不在没有参数的bjam调用上构建,可以将该目标标记为显式的,例如

explicit install_main_$(project-name) ;
除非明确要求,否则将禁止安装main_示例。为了防止main_示例的生成,请为
main_$(项目名称)
$(项目名称)添加
explicit

explicit main_$(project-name) ;
explicit $(project-name).o ;
或全部:

explicit install_main_$(project-name) main_$(project-name) $(project-name).o ;

请注意,将
main\u$(项目名称)
声明为
explicit
,而不将
install\u main\u$(项目名称)
声明为
explicit
,或者将
main\u$(项目名称)
声明为
explicit
是没有意义的,就好像请求构建一个目标一样,它的所有依赖目标也将被要求构建,即使这些依赖关系是显式的

,谢谢,这非常有用。只是为了澄清一些事情——规则不是按顺序执行的,它们只是提供了一个con