身為組裝工,常常執行下面的指令
- ./configure
- make
- 組裝
用了那麼久從來沒有思考過這是什麼樣的東西,慚愧之餘趕快惡補一下。
目錄
Overview
緣由:
雖然C語言號稱高移植性,然而遺憾的是因為System call, library等介面早期並沒有規範。這造成使用C語言開發多平台軟體的時候需要針對不同的平台做許多的檢查。後來GNU針對這部份提出了autotool工具減輕開發的負擔。
如果懶得看元件簡介,請直接看Overoview結論
Autotool 元件
從Wikipedia可以看到GNU Build system的項目中有提到三個元件: * Autoconf * Automake * Libtool
Autoconf - GNU Project - Free Software Foundation (FSF)
從這邊可以看到configure
負責產生
- Makefile
- 讓你編譯程式
- C option用的header file (optional)
config.h
configure.status
- 重新自動產生上面的資料
configure.cache
(optional)- cache之前configure偵測的系統結果
套件中有幾個程式
autoscan
- 產生
configure.ac
- 產生
autoconf
- 從
configure.ac
中產生configure
- 為何是
或
呢?這和autoconf的版本有關
- 從
autoheader
- 從
configure.ac
產生config.h.in
- 從
ifnames
- 掃描C原始碼,抽出ifdef的資訊
Automake - GNU Project - Free Software Foundation (FSF)
套件中有兩個程式
- automake
- 從
Makefile.am
中產生Makefile.in
,讓configure
執行時可以產生Makefile
- 從
- aclocal
- 從
configure.ac
或configure.in
產生aclocal.m4
- 從
GNU Libtool - The GNU Portable Library Tool
- 提供抽象化的介面處理函式庫的平台差異問題,本篇暫不討論。
另外GNU 其他針對移植性輔助的套件有
- GNU gettext
- i18n套件,協助專案中的各國語言訊息開發。
- pkg-config
- 提供開發時的函式庫資訊,開發者不需要知道函式庫的路徑和旗標,直接問pkg-config就好。
- GCC
- 全名是
GNU Compiler Collection
- 全名是
合體
從Wikipedia的圖:Autoconf-automake-process解釋的非常清楚。
回到最前面,我們可以觀察到autotool的目的就是
- 產生平台上可以編譯的環境
為了達到這樣的目的,系統需要做到下面的功能
- 檢查平台環境
- 產生Makefile
因此,開發者最少要告訴autotools 所需平台環境 和 產生Makefile 這兩項資訊。這也是configure.ac
和Makefile.am
存在的目的。也就是說,開發者需要自行設定configure.ac
和Makefile.am
。
而這些錯綜複雜的關係可以描述如下
- autotool先產生
configure.ac
(透過autoscan
或是自幹) autoreconf
吃configure.ac
和Makefile.am
產生confgure
,config.h.in
, 和Makefile.in
- autoreconf細節
- 吃
configure.ac
,呼叫aclocal
產生aclocal.m4
- aclocal是給autotools中自訂專案檢查編譯巨集用。
- 吃
configure.ac
和aclocal.m4
,呼叫autoheader
產生config.h.in
- 吃
configure.ac
和aclocal.m4
,呼叫autoconf
產生configure
- 吃
configure.ac
和aclocal.m4
和各處的Makefile.am
,呼叫automake
產生Makefile.in
- 吃
- 吃
範例
測試環境
- Ubuntu 12.04.4
測試程式
範例程式細節在這邊,檔案各別重新分配到src
, include
, libs
這三個目錄。不想看code只要知道每個檔案都有參考到某個自訂的header file就好了。
1 2 3 4 5 6 7 8 |
|
導入Autotools
簡述一下流程
- 使用
autoscan
產生configure.ac
範本 - 手動更改
configure.ac
- 寫
Makefile.am
,根目錄以及需要編譯的地方都要一份 autoreconf --install
產生檔案- 替代方案:執行下面程式
aclocal
autoheader
automake --add-missing
autoconf
- 替代方案:執行下面程式
configure
make
make install
安裝或make dist
打包
configure.ac
執行autoscan
後會產生configure.scan
檔案,把這個檔案rename成configure.ac
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
|
接下來就是更動configure.ac
,更動完和原本的差別如下:
1 2 3 4 5 6 7 8 9 10 |
|
簡單說明如下
- 更改套件版本資訊
- 刪除
AC_CONFIG_SRCDIR
- 設定automake
foreign
表示這不是標準的GNU Coding Standard,因此不會檢查額外的檔案如NEWS
,README
,ChangeLog
等。- 共用編譯參數
AC_PROG_RANLIB
表示要使用static library
Makefile.am
前面提到,每個目錄都要有一個Makefile.am
。關於Makefile.am
語法,可以參考 Alexandre Duret Lutz: Autotools Tutorial大略了解。更詳細的部份可以看Automake手冊:8.3 Building a Shared Library
範例中Makefile.am
如下:
- ./Makefile.am: 基本上就是依照列出的順序編譯
1
|
|
- libs/Makefile.am
1 2 3 4 5 6 |
|
最上面形式就是要裝到目錄
_Keyword
,所以表示我們要產生liba.a
和libb.a
,安裝時放在/usr/local/lib
下面、指定library由哪些原始程式檔案組成、同時要把header files放在/usr/local/include
下。(configure沒指定預設prefix為/usr/local)
- src/Makefile.am
1 2 3 4 5 |
|
一樣的形式:要裝到目錄
_Keyword
。這邊宣告要安裝到/usr/loca/bin
、要link liba.a
和libb.a
、並且5指定執行檔的原始程式檔案。
經過上面的處理,我們多了三個Makefile.am
和configure.ac
以及一些暫存檔案。新的樹狀目錄列表如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 |
|
產生configure
並編譯
如前所述,直接使用autoreconf --install
就可以了
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 |
|
./configure結果節錄如下
1 2 3 4 5 6 7 8 9 10 11 |
|
幾點要注意的:
config.status
被產生,並且被執行時生出config.h
以及各目錄的的Makefile
- 這邊指定prefix為
/tmp/build
,因此make install
可以看到被安裝目錄樹狀結構如下:
1 2 3 4 5 6 7 8 9 |
|
參考資料及資源
強烈推荐 Alexandre Duret Lutz: Autotools Tutorial,主要的想法和資料都是從這邊出來。而且他寫的更加詳細、更加易懂。
- FSF官方資料:
- Wikipedia: GNU build system
- Wikipedia: Autoconf
- 陳雍穆: automake
- $4: GNU Build System (aka Autotools)
- 石頭閒語: Hello Autoconf, the GNU Build System
- GNU autoconf (automake) “Hello World” step-by-step example
- Alexandre Duret Lutz: Autotools Tutorial
- Autotools Mythbuster
- 今天的 Tetralet 又在唧唧喳喳了: 利用 Autotools 來建立 Makefile 檔案