使用 CUDA/custom 语言和 $(eval) 规则创建的 automake

automake with CUDA/custom language and $(eval) rule creation

我需要构建一些混合纯 C 文件和 CUDA 文件的内部库。此外,可以使用不同的预处理器选项从相同的源构建不同的库。

我已经设法得到一些有用的东西,但发生的事情是我不喜欢 我必须显式定义 CUDA 对象,因为它们可以很容易地从 _SOURCES 中推断出来变量:

$猫Makefile.am

AUTOMAKE_OPTIONS = foreign

NVCC=cc
cuda_libs = libfoobar1.a libfoobar2.a

noinst_LIBRARIES = $(cuda_libs)

foobar_sources = foo.c bar.cu
libfoobar1_a_SOURCES  = $(foobar_sources)
libfoobar1_a_CPPFLAGS = -DLIB1
libfoobar1_a_LIBADD   = libfoobar1_a-bar.o # CUDA object explicit definition 
libfoobar2_a_SOURCES  = $(foobar_sources)
libfoobar2_a_CPPFLAGS = -DLIB2
libfoobar2_a_LIBADD   = libfoobar2_a-bar.o # CUDA object explicit definition 

$(eval include cuda.mk) # why eval? Check comment #1

clean-local:
    rm -rf libfoobar2_a-bar.o libfoobar1_a-bar.o

$猫cuda.mk

# $(get_conincal names)
get_canonical = $(subst .,_,$(1))

# $(call cuda_rule prefix) http://blog.jgc.org/2012/01/using-gnu-makes-define-and-eval-to.html
define cuda_rule
$(1)-%.o: %.cu
    $(NVCC) $(CUDA_CFLAGS) $($(1)_CPPFLAGS) --compiler-options="$($(1)_CFLAGS)" -c -o $$@ $$<
endef

$(foreach cuda_prefix,$(call get_canonical,$(cuda_libs)),$(eval $(call cuda_rule,$(cuda_prefix))))

如果我尝试概括 CUDA 对象定义,将它们移动到规则生成中,如下所示:

define cuda_rule
$(1)_LIBADD = $(addsuffix .o,$(addprefix $(1)-,$(basename $(filter %.cu,$($(1)_SOURCES)))))
[...]
endef

make 现在似乎没有得到规则,并且不知道如何构建 CUDA 对象:

ar cru libfoobar1.a libfoobar1_a-foo.o libfoobar1_a-bar.o
ar: libfoobar1_a-bar.o: No such file or directory

有什么想法吗? 提前致谢。

阿尔伯特

P.S。 All files如果你想和这个一起玩,你需要

一切都是关于如何读取 Makefile 和如何扩展变量的。

检查 automake 生成的 Makefile 可以看到 $eval 调用在 Makefile 的末尾结束。最终 Makefile 中的顺序似乎是:AM 变量、用户变量、AM 规则,最后是用户规则。当我们修改 AM 规则的先决条件时,我们必须在规则本身被解析之前进行修改,因为规则先决条件会立即扩展。

A rule is always expanded the same way, regardless of the form:

immediate : immediate ; deferred

         deferred

https://www.gnu.org/software/make/manual/html_node/Reading-Makefiles.html

由于 eval 函数始终为空字符串,我们可以将其分配给强制立即扩展的一次性变量。然后,它将与用户变量放在最终 Makefile 中的 AM 规则定义之前。

ignore:=$(eval include cuda.mk)