大家好,又见面了,我是你们的朋友全栈君。
引用自:
http://www.pigfoot.org/cc/devel/auto1/
Murray Cumming <murrayc@usa.net> Chen Chih-Chia <pigfoot@CDPA.nsysu.edu.tw>
May 28, 2005 (Updated)
Abstract
在 Unix 底下,automake 和 autoconf 常被用來管理 C/C 的專案。 如果您的專案是根據 GNU 的標準建構出來的,那麼它們能夠幫您節省很多 make 以及 configure 的時間。然而,萬事起頭難。希望這篇指南能夠為剛入門的程式設計師提供一些有用的資訊。
我不是 Unix 以及 autoconf, automake 的專家,所以我歡迎有建設性的批評與指教。
make and configure
這個 make tool 能夠用來管理多個檔案的專案。make 會用到您專案裡的 Makefile 這個檔案,這個檔案列出了各式的編譯以及連結步驟,目的,以及一些相依關係。多檔的專案與 GNU 的 make 工具程式是有很大的關係的。
configure 這個 script 被用來協助處理跨平台的編譯工作。一個合適的 configure script 能夠正確的解譯 Makefile.in 然後產生該平台相依的 Makefile。當然。產生 Makefile 之前必須經過很多測試來決定該平台的特性。
所以我們允許使用者執行 ‘./configure ‘ 然後再執行 ‘make ‘ 來根據自身的平台而編譯這個專案。
aclocal.m4
很明顯的,大部分寫好的 Makefile 和 configure script 看起來都非常的類似。事實上,GNU 提供了一些關於這些檔案的細部描述。因此,GNU 寫出了 automake 以及 autoconf 來簡化處理這些過程,並且確保 Makefile 以及 configure script 能夠遵守 GNU 標準。
這裡是這些工具的簡單的介紹。我這裡也提供了範例供您測試使用。
注意 :這些工具使用 m4 程式語言。 aclocal 增加 aclocal.m4 這個檔案到您的專案目錄,因為包含了一些需要用到的 m4 巨集。
autoconf
autoconf 會尋找叫做 configure.in 這個檔案,然後會根據他找到的巨集而生出 configure script。
注意要的是 autoscan 可以用來產生一個可能使用的 configure.in。它會測試你的原始檔案,然後放進一些建議值到一個叫做 configure.scan 的檔案。當然您必須改名成 configure.in 。
不管什麼時候,您在 configure.in 加入一個巨集時,然後必須執行 aclocal 和 autoconf ,因為 aclocal 會掃描 configure.in 然後找出它必須提供的巨集。
Lines which every configure.in should have
每一個 configure.in 應該有底下這幾行:
代码语言:javascript复制AC_INIT(hello.cc)
AM_INIT_AUTOMAKE(hello,0.1)
AC_PROG_CC
AC_PROG_CXX
AC_PROG_INSTALL
AC_OUTPUT(Makefile)
AC_INIT 這個巨集以一個原始檔當作參數。它會檢查該檔是否存在,也會檢查目錄是否存在。
AM_INIT_AUTOMAKE 這行增加了幾個標準的檢查。它是以程式名稱以及版本號碼當作參數。
AC_PROG_CC 指出了該原始檔是用 C 寫成的。假如原始檔是用 C 寫成的,那麼應該改成 AC_PROG_CXX 。
AC_PROG_INSTALL 會產生安裝目的地,好讓使用者打 make install 便能安裝這套軟體。
AC_OUTPUT 指出應該產生的 Makefile 檔案名稱。
Using a Config Header
AM_CONFIG_HEADER(config.h) 這行指出了您將會使用 config.h 檔。autoconf 將會需要 config.h.in ,並將之處理成 config.h。這是你的原始檔案中,透過 #define 定義的標頭檔,好提供一個方式讓人們為它們的平台自訂 configuration。config.h.in 能夠被 autoheader 這個工具程式自動產生。
然而,在你的專案中,你需要 stamp-h 這個檔案來確保 automake 從 config.h.in 重新產生 config.h。執行 ‘touch stamp-h ‘ 讓您的專案新增這個檔案。
automake
automake 會尋找 Makefile.am 這個檔案,然後依據它找到的巨集產生 Makefile.in。當然,這個會在稍後的 configure script 用到。
GNU-style projects, or not
因為預設值 automake 會嘗試產生 GNU-style 的專案,因此如果一些該有的檔案不存在,automake 會向您抱怨。所以您可以用以下指令產生需要的空白文件:
touch NEWS README AUTHORS ChangeLog
如果您不需要 GNU-style 的檔案,您可以在您的 Makefile.am 增加以下這行:
AUTOMAKE_OPTIONS = foreign
Telling automake about your source files
使用下面這兩行來命名您的程式名稱,以及列出它的原始程式:
代码语言:javascript复制bin_PROGRAMS = hello
hello_SOURCES = hello.h hello.cc main.cc
注意:第二個變數的前置是依據第一個變數的。
The Whole Process
假設您已經概略的編輯完 Makefile.am 和 configure.in (底下有範例),藉由底下的指令,您應該能夠 build 您專案了:
代码语言:javascript复制autoheader
touch NEWS README AUTHORS ChangeLog
touch stamp-h
aclocal
autoconf
automake
./configure
make
當你想完整重新 build 專案,請重複最後五個步驟。
* autoheader – creates config.h.in * aclocal – adds aclocal.m4 to directory. * autoconf – creates configure from configure.in * automake – Creates Makefile.in from Makefile.am * ./configure – creates Makefile from Makefile.in
Sub Directories
當 然,專案的檔案應該被組織化的放在子目錄裡。理想上來說,原始檔和 makefile,configure scripts,以及 README 等等這些檔案,應該都放在專案的 src 這個子資料匣中。多層式的專案我們把它叫做 Deep 專案。我會列出應該處理的步驟,但是你依然可以看看範例程式。
當使用子目錄的時候,你必須坐下的步驟:
1. 增加 SUBDIRS 這一項到最頂層的 Makefile.am。例如:
SUBDIRS = doc intl po src tests
注意這些資料匣的名稱要以空白區分。
2. 在每一個子目錄中都要新增一個 Makefile.am。但是不需要 configure.in。而且要確定最頂層的 configure.in 中的 AC_OUPUT 巨集要加入檔名以產生 Makefile。
For sub directories containing additional source code
3. 增加 AC_PROG_RANLIB 巨集到您的 configure.in 。這允許您在子目錄中 build 的 code 能夠暫時放到某個暫存目錄,以便之後用來和其他 code 作連結之用。
4. 增加一些巨集到 src 下的任何原始檔目錄的 Makefile.am。這將會 build 一個不會安裝的函式庫。你需要給定以 lib 字母為開頭的函式庫名稱,並且指定該函式庫的原始碼以及標頭檔,例如:
代码语言:javascript复制noinst_LIBRARIES = libfoo.a
libfoo_a_SOURCES = foo.h foo.cc
INCLUDES = -I@top_srcdir@/src/includes
注意 SOURCES 巨集會使用底線 ‘_’ 來代替函式庫的名稱的點 ‘.’。而且要使用 top_srcdir 這個變數來參考到專案的最頂端。
5. 在上一層目錄使用 Makefile.am 的 LDADD 這個巨集,來連結任何可能用到這個暫時函式庫的 Code。例如:
LDADD = foofiles/libfoo.a
For sub directories containing non-source files
3. 一個子目錄下的 Makefile.am 應該包含像底下的這行:
EXTRA_DIST = somefile.txt someotherfile.html
這會告訴 automake 您要發布這些檔案,但是它們不需要編譯。
Example Files
底下就是範例檔了。它是一個使用一個標準函式庫的 C 專案。
看看 autoconf 和 automake 的手冊來參閱使用到的一些巨集以及變數。我不要這些範例因為註解而變的難以閱讀。
這個 Deep 專案的架構如下:
helloworld_cc
configure.in Makefile.am src Makefile.am helloworld.h helloworld.cc main.cc foofiles Makefile.am foo.h foo.cc
configure.in
代码语言:javascript复制AC_INIT(src/hello.cc)
AM_INIT_AUTOMAKE(hello,0.1)
AM_CONFIG_HEADER(config.h)
AC_PROG_CC
AC_PROG_CXX
AC_PROG_INSTALL
AC_PROG_RANLIB
AC_OUTPUT(Makefile src/Makefile src/foofiles/Makefile)
Makefile.am
SUBDIRS = src
Makefile.am for the src directory
代码语言:javascript复制bin_PROGRAMS = hello
INCLUDES = foofiles
hello_SOURCES = hello.h hello.cc main.cc
SUBDIRS = foofiles
LDADD = foofiles/libfoo.a
Makefile.am for foofiles directory under src
代码语言:javascript复制noinst_LIBRARIES = libfoo.a
libfoo_a_SOURCES = foo.h foo.cc
INCLUDES = -I@top_srcdir@/
您可以下載這個簡單的範例檔: helloworld_cc-0.3.tar.gz
Related Link
- Origin article
- GNU Autoconf, Automake, and Libtool
- C-Scene: Multi-File Projects and the GNU Make Utility
- GNU’s automake and autoconf manuals
- Learning autoconf and automake
- Learning the GNU Development tools
- Programming with GNU Software, Mike Loukides & Andy Oram
发布者:全栈程序员栈长,转载请注明出处:https://javaforall.cn/127614.html原文链接:https://javaforall.cn