将Autotools用于具有特定于平台的源代码的项目

时间:2013-03-13 23:42:34

标签: c assembly autotools autoconf automake

我正在开发一个目前用C编写的项目,但我计划在ASM中为至少两个平台(x86_64和arm)编写一些函数。所以我可能有一些源文件:

  • 通用/ one.c
  • 通用/ two.c
  • 通用/ three.c
  • 臂/ one.s
  • x86_64的/ two.s

我希望配置脚本在可能的情况下在.c文件上选择.s文件。所以建立在arm上将是one.s,two.c,three.c等。

使用Automake很难或不可能做到这一点。但如果我放弃Automake,我将不得不追踪自己的依赖(呃)。

最好的方法是什么?

3 个答案:

答案 0 :(得分:3)

这就是我的所作所为。

<强> configure.ac

...
AC_CANONICAL_SYSTEM
AM_PROG_AS
AC_PROG_CC
...
PROC=""
AS_CASE([$host_cpu], [x86_64], [PROC="x86_64"], [arm*], [PROC="arm"])

AM_CONDITIONAL([CPU_X86_64], [test "$PROC" = "x86_64"])
AM_CONDITIONAL([CPU_ARM], [test "$PROC" = "arm"])
AM_CONDITIONAL([CPU_UNDEFINED], [test "x$PROC" = "x"])

<强> Makefile.am

lib_LTLIBRARIES = libfoo.la
libfoo_la_SOURCES = \
$(top_srcdir)/generic/three.c

if CPU_ARM
libfoo_la_SOURCES += $(top_srcdir)/arm/one.s \
$(top_srcdir)/generic/two.c
endif

if CPU_X86_64
libfoo_la_SOURCES += $(top_srcdir)/generic/one.c \
$(top_srcdir)/x86_64/two.s
endif

if CPU_UNDEFINED
libfoo_la_SOURCES += $(top_srcdir)/generic/one.c \
$(top_srcdir)/generic/two.c
endif

答案 1 :(得分:2)

automake手册的Conditional Sources部分应指向正确的方向。您需要AC_CANONICAL_HOST中的configure.ac,然后根据$host的值做出决定。

如果两个文件可以编译到同一个对象,

automake将不会喜欢它。如果您无法像手册的链接部分那样重命名来源,则可能需要尝试这样的操作(确保subdir-objects中有AM_INIT_AUTOMAKE

# Note the $() isn't a shell command substitution.
# The quoting means it'll be expanded by `make'.
MODULE_ONE_OBJ='generic/one.$(OBJEXT)'
MODULE_TWO_OBJ='generic/two.$(OBJEXT)'
case $host in
  # ...
  arm*)
    MODULE_ONE='arm/one.$(OBJEXT)'
    ;;
  x86_64)
    MODULE_TWO='x86/two.$(OBJEXT)'
    ;;
esac
AC_SUBST([MODULE_ONE])
AC_SUBST([MODULE_TWO])

Makefile.am

bin_PROGRAMS = foo
foo_SOURCES = foo.c
EXTRA_foo_SOURCES = arm/one.s x86/two.c
foo_LDADD = $(MODULE_ONE) $(MODULE_TWO)
foo_DEPENDENCIES = $(MODULE_ONE) $(MODULE_TWO)

答案 2 :(得分:2)

您可以使用AC_CANONICAL_HOST,然后有条件地选择正确的子目录。例如,在configure.ac

AC_CANONICAL_HOST
AC_SUBST([USE_DIR],[$host_cpu])
test -d $srcdir/$USE_DIR || USE_DIR=generic

然后在Makefile.am

SUBDIRS = $(USE_DIR) common

common/Makefile.am

LDADD = ../$(USE_DIR)/libfoo.a

以及每个${host_cpu}/Makefile.am

noinst_LIBRARIES = libfoo.a
libfoo_a_SOURCES = one.s ../common/two.c

这使用的目录结构与您描述的略有不同。所有平台上使用的C文件都将放在common中,并链接到在特定于平台的目录中构建的便捷库。如果某些c文件仅在某些平台上使用,则可以将它们放在一起,并在Makefile.am中为需要它们的平台显式引用它们。