Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/selenium/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Installation 使用automake安装包含大量文件的数据目录树_Installation_Autotools_Autoconf_Automake - Fatal编程技术网

Installation 使用automake安装包含大量文件的数据目录树

Installation 使用automake安装包含大量文件的数据目录树,installation,autotools,autoconf,automake,Installation,Autotools,Autoconf,Automake,我有一个数据目录,我想自动生成安装和卸载目标。本质上,我只想将这个目录逐字复制到数据目录,通常,我可能会单独列出所有文件,如 dist_whatever_DATA=dir/subdir/filea ... 但当我的目录结构看起来像这样时,问题就出现了 *root *subdir *~10 files *subdir *~10 files *subdir *~700 files *subdir ... ~20 subdirs 我无法列出Makefile.am中包含的所有

我有一个数据目录,我想自动生成安装和卸载目标。本质上,我只想将这个目录逐字复制到数据目录,通常,我可能会单独列出所有文件,如

dist_whatever_DATA=dir/subdir/filea ...
但当我的目录结构看起来像这样时,问题就出现了

*root
 *subdir
  *~10 files
 *subdir
  *~10 files
 *subdir
  *~700 files
 *subdir
 ...
 ~20 subdirs
我无法列出Makefile.am中包含的所有1000多个文件。那太荒谬了


我还需要保留目录结构。我应该注意到,这些数据根本不是由构建过程生成的,实际上大部分是短录音。所以,我不想让automake“检查”我想安装的每个文件是否都已创建,因为它们要么在那里,要么不在那里,不管有什么文件,我知道我想安装它,不管没有什么文件,都不应该安装。我知道这是在其他地方不使用通配符指令的理由,但所有可能的原因在这里都不适用。

我将使用脚本生成一个
Makefile
片段,列出所有文件:

echo 'subdir_files =' > subfiles.mk
find subdir -type f -print | sed 's/^/  /;$q;s/$/ \\/' >> subfiles.mk
然后从主
Makefile.am
中包含此
子文件.mk

include $(srcdir)/subfiles.mk
nobase_dist_pkgdata_DATA = $(subdir_files)

第二个选项是
EXTRA_DIST=subdir
,然后编写自定义
install data local
卸载local
规则

这里的问题是
EXTRA_DIST=subdir
将分发
subdir/
中的所有文件,包括备份文件、配置文件(例如来自VCS)以及其他您不想分发的文件


使用如上所述的脚本,您可以筛选真正想要分发的文件。

我将编写一个脚本(作为单独的shell脚本,或在
Makefile.am
中编写),这是作为目标的一部分运行的。

我发现单独安装数百个文件会导致调用
makeinstall
的时间非常长。我有一个类似的例子,我想安装数百个文件,保留目录结构,我不想每次向集合中添加或从集合中删除文件时都更改Makefile.am

我在发行版中包含了LZMA文件归档,并制定了如下自动生成规则:

GIANTARCHIVE = My_big_archive.tar.lz

dist_pkgdata_DATA = $(GIANTARCHIVE)

install-data-hook:
    cd $(DESTDIR)$(pkgdatadir); \
    cat $(GIANTARCHIVE) | unlzma | $(TAR) --list > uninstall_manifest.txt; \
    cat $(GIANTARCHIVE) | unlzma | $(TAR) --no-same-owner --extract; \
    rm --force $(GIANTARCHIVE); \
    cat uninstall_manifest.txt | sed --expression='s/^\|$$/"/g' | xargs chmod a=rX,u+w

uninstall-local:
    cd $(DESTDIR)$(pkgdatadir); \
    cat uninstall_manifest.txt | sed --expression='s/ /\\ /g' | xargs rm --force; \
    rm --force uninstall_manifest.txt

这样,automake会在
$(pkgdata)
目录中安装
My_big_archive.tar.lz
,并在那里提取它,列出其中的所有文件,以便以后卸载它们。这也比将每个文件列为安装目标要快得多,即使您要自动生成该列表。

请注意:第一个文件不起作用,因为它在“make[2]:execvp:/bin/bash:Argument list too long”哇!我正在生成一些带有相当大的文件列表的
Makefile
s,但我还没有意识到有一天我会达到命令行大小限制!你能举一个第二种选择的例子吗?如果我只是“cp-Rf”,我得到了错误的权限,我需要在cp之后使用chmod(或者在cp之前使用umask)。我查看了自动生成的规则,它们使用$(INSTALL_DATA)而不是cp,但在这种情况下,需要指定所有文件,因此需要“find”等。最好的方法是什么,在install data local中安装整个目录的最方便的方法?@marcin类似于此,find命令有一个printf输出选项,它可能更容易理解,然后通过管道连接到sed。为什么要将它安装到
$(pkgdatadir)
?只需从
install data hook
中的
$(srcdir)
中提取它即可。使用类似于
EXTRA\u DIST=giant\u archive.tar.lzma这样的方法来分发它。三个小建议,与实际问题无关。我将用
yyyy@adl替换猫xxx | yyy | zzz
,谢谢!我一直认为在脚本中使用长选项可以使脚本更易于阅读,但可移植性更好。