1
2
3
4
5
6
7
8
9
|
//根據configure.in和Makefile.am生成makefile的步驟,基於UBUNTU 12.04
1.autoscan (可選)
2.aclocal
3.autoconf
4.autoheader(可選)
5.libtoolize --automake --copy --debug --force(可選)
6.automake --add-missing
7.autoreconf –f –i –Wall,no–obsolete(可選)
8../configure
|
簡單的方式:
如果拿到的工程文件中,沒有Makefile文件,而只有configure.in和Makefile.am文件,我們是不能夠直接進行編譯的,必須在UBUNTU等Linux系統下,根據configure.in和Makefile.am文件生成編譯所需的Makefile文件。具體操作步驟如下:
1、執行autoscan,然后執行aclocal,產生aclocal.m4文件
aclocal是一個perl 腳本程序,它的定義是:“aclocal – create aclocal.m4 by scanning configure.ac”。 aclocal根據configure.in文件的內容,自動生成aclocal.m4文件。而aclocal.m4文件中,包含了生成configure文件所必須的宏。
2、執行autoconf,生成configure文件
autoconf會根據configure.in和aclocal.m4文件,生成configure文件。其實,autoconf就是把configure.in和aclocal.m4文件中定義的內容, 變成檢查系統特性、環境變量、軟件必須的參數的shell腳本。
3、執行automake命令,產生Makefile.in
具體命令為:automake –add-missing
automake會根據Makefile.am文件產生一些文件,包含最重要的Makefile.in。前面所生成的configure,會根據Makefile.in文件,來生成最終的Makefile文件。
4、執行configure命令,生成Makefile文件
這樣,就產生了編譯所需要的Makefile文件。運行make,即可編譯。
復雜點的方式:
為一個項目源文件生成makefile並make的步驟如下:
操作在包含源文件的項目目錄下進行。
- (1)運行autoscan,生成文件configure.scan
- (2)修改configure.scan,改名為configure.in
- (3)運行autoheader,生成文件configure.h.in(現在一般改為configure.ac)
- (4)運行libtoolize,生成ltmain.sh
- (5)運行allocal,生成aclocal.m4
- (6)運行autoconf,生成configure
- (7)運行automake,生成makefile.in,每個包含makefile.am的子目錄都生成makefile.in。automake -a選項可以補齊文件config.guess,config.sub,install-sh,missing,depcomp
- (8)運行./configure,生成config.status,config.h,makefile
- (9)運行make,生成中間文件對象文件,庫文件,最后生成可執行文件
- (10)運行make install,相應的可執行文件,庫文件,頭文件拷貝到系統相應位置。
configure運行
configure是一個shell腳本文件,由autoconf生成,它自動為源碼包配置編譯連接選項,適應不同的硬件平台和POSIX操作系統,輸出所需要的Makefile。
configure主管檢查你的系統,把結果存放到config.status中,config.status根據它的檢查結果實際執行正確的動作。
configure檢查與系統相關的一系列變量,這些變量存儲到文件config.status中,供makefile調用。這些變量包括編譯連接時需要的程序,這些程序在系統中的位置(目錄),調用這些程序的選項,比如編譯器的目錄,編譯器的選項-g是否支持等。configure能猜出它運行的系統的規范名字cpu–vendor–os,它通過運行腳本文件config.guess輸出變量uname來猜出。configure能識別很多系統名字的別名,它通過運行腳本文件config.sub把系統名字變成規范名字。
make運行
makefile.am對makefile的影響:它根據SUBDIRS = add sub讓make遞歸進入每個子目錄處理子目錄的Makefile。根據main_LDADD = add/libadd.la sub/libsub.la為main連接libadd.la和libsub.la庫。
configure.in對makefile的影響:
根據AC_PROG_LIBTOOL讓libtool完成編譯連接工作。
根據AC_CONFIG_HEADERS([config.h])只需傳遞預處理宏-DHAVE_CONFIG_H給編譯器。
makefile中很多與系統相關的信息都是通過變量獲取的,這些變量之前已經由configure檢查好存放在config.status里面,預處理 宏存放在config.h里面。比如我們要用到的編譯器CC,編譯器選項CFLAGS等。makefile中的變量完成替換后,開始實際執行命令,它會遞 歸執行每一個子目錄下的makefile,生成對象文件,連接庫文件,最后連接成可執行文件。
交叉編譯 Cross-compiling
Q:為別的平台編譯可執行程序怎么做?
交叉編譯就是在目前的平台上為別的目標平台生成可執行程序或庫。可以在運行configure時通過–build,–host,–target參數實現交叉編譯。
例如:
1
|
./configure --build=i686-pc-linux-gnu --host=m68k-coff
|
–build=build-type :configure和compile軟件包的系統類型。默認情況等於config.guess給出的系統類型
–host=host-type :運行軟件包的系統類型。默認情況等於build類型
–target=target-type :很少用,默認情況等於host類型。
交叉編譯時,如果編譯器,連接器,匯編器名字不是以host_type為前綴,configure都會發出警告。
要搭建交叉變異環境,如交叉編譯用的編譯器,連接器,匯編器跟本地的不一樣,一般以host_type為前綴,如arm-pc-linux-gcc。
安裝目錄
Q:make install時,文件都安裝到哪里去了?
prefix:安裝目錄的前綴。默認情況下/usr/local 。
bindir:安裝時拷貝可執行文件到此目錄。默認情況下/usr/local/bin 。
includir:安裝時拷貝頭文件到此目錄。默認情況下/usr/local/include 。
libdir:安裝時拷貝庫文件到此目錄。默認情況下/usr/local/libs 。
定制自己的安裝目錄,可以–prefix 和 –exec-prefix 給configure。
例如:./configure –prefix=/usr 。
Configure,Makefile.am, Makefile.in, Makefile文件之間關系

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
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
|
1.autoscan (autoconf): 掃描源代碼以搜尋普通的可移植性問題,比如檢查編譯器,庫,頭文件等,生成文件configure.scan,它是configure.ac的一個雛形。
your source files --- [autoscan*] --- [configure.scan] --- configure.ac
2.aclocal (automake):根據已經安裝的宏,用戶定義宏和acinclude.m4文件中的宏將configure.ac文件所需要的宏集中定義到文件 aclocal.m4中。aclocal是一個perl 腳本程序,它的定義是:“aclocal - create aclocal.m4 by scanning configure.ac”
user input files optional input process output files
================ ============== ======= ============
acinclude.m4 - - - - -.
V
.-------,
configure.ac -------------------------|aclocal|
{user macro files} --| |------- aclocal.m4
`-------'
3.autoheader(autoconf): 根據configure.ac中的某些宏,比如cpp宏定義,運行m4,聲稱config.h.in
user input files optional input process output files
================ ============== ======= ============
aclocal.m4 - - - - - - - .
|
V
.----------,
configure.ac ------------------------|autoheader|----- autoconfig.h.in
`----------'
4.automake: automake將Makefile.am中定義的結構建立Makefile.in,然后configure腳本將生成的Makefile.in文件轉換 為Makefile。如果在configure.ac中定義了一些特殊的宏,比如AC_PROG_LIBTOOL,它會調用libtoolize,否則它 會自己產生config.guess和config.sub
user input files optional input processes output files
================ ============== ========= ============
.--------,
| | - - -- COPYING
| | - - -- INSTALL
| |------- install-sh
| |------- missing
|automake|------- mkinstalldirs
configure.ac ------------------------| |
Makefile.am ------------------------| |------- Makefile.in
| |------- stamp-h.in
.---+ | - - -- config.guess
| | | - - -- config.sub
| `------+-'
| | - - - -- config.guess
|libtoolize| - - - -- config.sub
| |--------- ltmain.sh
| |--------- ltconfig
`----------'
5.autoconf:將configure.ac中的宏展開,生成configure腳本。這個過程可能要用到aclocal.m4中定義的宏。
user input files optional input processes output files
================ ============== ========= ============
aclocal.m4 ,autoconfig.h.in - - - - - - -.
V
.--------,
configure.ac ------------------------|autoconf|------- configure
6. ./configure的過程
.-------------- [config.cache]
configure* --------------------------+-------------- config.log
|
[config.h.in] -. v .--- [autoconfig.h]
+-------> config.status* -+
Makefile.in ---' `--- Makefile
7. make過程
[autoconfig.h] -+--- make* ---- 程序
Makefile ---'
----------
config.site - - --| |
config.cache - - --|configure| - - -- config.cache
| +-,
`-+-------' |
| |----- config.status
config.h.in --------|config- |----- config.h
Makefile.in --------| .status|----- Makefile
| |----- stamp-h
| +--,
.-+ | |
| `------+--' |
ltmain.sh --------|ltconfig|-------- libtool
| | |
`-+------' |
|config.guess|
| config.sub |
`------------'
----------
Makefile -------| |
config.h -------| make |
{project sources} -----------------| |--------- {project targets}
.-+ +--,
| `--------' |
| libtool |
| missing |
| install-sh |
|mkinstalldirs|
`-------------'
|
針對上面提到的 各個命令,我們再做些詳細的介紹
//http://www.laruence.com/2009/11/18/1154.html
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
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
|
1. autoscan
autoscan是 用來掃描源代碼目錄生成configure.scan文件的 .autoscan
可以用目錄名做為參數
,但如果你不使用參數的 話,那么autoscan將認為使用的是當前目錄.
autoscan將掃描你所指定目錄中的 源文件,並創建configure.scan文件.
2. configure.scan
configure.scan包含了系統配置的 基本選項,里面都是 一些宏定義.我們需要將它改名為
configure.in
3. aclocal
aclocal是 一個perl 腳本程序.aclocal根據configure.in文件的 內容
,自動生成aclocal.m4文件.aclocal的 定義是 :"aclocal - create
aclocal.m4 by scanning configure.ac".
4. autoconf
autoconf是 用來產生configure文件的 .configure是 一個腳本,它能設置
源程序來適應各種不同的操作系統平台
,並且根據不同的 系統來產生合適的 Makefile,從而可以使
你的源代碼能在不同的操作系統平台上被編譯出來
.
configure.in文件的 內容是 一些宏,這些宏經過autoconf 處理后會變成檢查系統
特性
.環境變量.軟件必須的 參數的 shell腳本.configure.in文件中的 宏的 順序並沒
有規定
,但是 你必須在 所有宏的 最前面和最后面分別加上AC_INIT宏和AC_OUTPUT宏.
在
configure.ini中:
#號表示注釋,這個宏后面的 內容將被忽略.
AC_INIT(FILE)
這個宏用來檢查源代碼所在
的 路徑.
AM_INIT_AUTOMAKE(PACKAGE, VERSION)
這個宏是 必須的 ,它描述了我們將要生成的 軟件包的 名字及其版本號:PACKAGE是軟件包
的名字
,VERSION是 版本號.當你使用make dist命令時,它會給你生成一個類似
helloworld-1.0.tar.gz的 軟件發行包,其中就有對應的 軟件包的 名字和版本號.
AC_PROG_CC
這個宏將檢查系統所用的
C編譯器.
AC_OUTPUT(FILE)
這個宏是
我們要輸出的 Makefile的 名字.
我們在
使用automake時,實際上還需要用到其他的 一些宏,但我們可以用aclocal 來幫
我們自動產生
.執行aclocal后我們會得到aclocal.m4文件.
產生了
configure.in和aclocal.m4 兩個宏文件后,我們就可以使用autocon
f來產生configure文件了.
5. Makefile.am
Makefile.am是 用來生成Makefile.in的 ,需要你手工書寫.Makefile.
am中定義了一些內容:
AUTOMAKE_OPTIONS
這個是
automake的 選項.在 執行automake時,它會檢查目錄下是 否存在 標准
GNU軟件包中應具備的各種文件,例如AUTHORS.ChangeLog.NEWS等文件.
我們將其設置成
foreign時,automake會改用一般軟件包的 標准來檢查.
bin_PROGRAMS
這個是
指定我們所要產生的 可執行文件的 文件名.如果你要產生多個可執行文件,
那么在各個名字間用空格隔開
.
helloworld_SOURCES
這個是
指定產生"helloworld"時所需要的 源代碼.如果它用到了多個源文件,
那么請使用空格符號將它們隔開
.比如需要helloworld.h,helloworld.c那么請寫成:
helloworld_SOURCES= helloworld.h helloworld.c.
如果你在
bin_PROGRAMS定義了多個可執行文件,則對應每個可執行文件都要定義相對的
filename_SOURCES.
6. automake
我們使用
automake --add-missing來產生Makefile.in.
選項
--add-missing的 定義是 "add missing standard files
to package",它會讓automake加入一個標准的 軟件包所必須的 一些文件.
我們用
automake產生出來的 Makefile.in文件是 符合GNU Makefile慣例
的
,接下來我們只要執行configure這個shell 腳本就可以產生合適的 Makefile 文
件了
.
7. Makefile
在
符合GNU Makefiel慣例的 Makefile中,包含了一些基本的 預先定義的 操作:
make
根據
Makefile編譯源代碼,連接,生成目標文件,可執行文件.
make clean
清除上次的
make命令所產生的 object文件(后綴為".o"的 文件)及可執行文件.
make install
將編譯成功的
可執行文件安裝到系統目錄中,一般為/usr/local/bin目錄.
make dist
產生發布軟件包文件(即
distribution package).這個命令將會將可執行文件及相關
文件打包成一個
tar.gz壓縮的 文件用來作為發布軟件的 軟件包.
它會在
當前目錄下生成一個名字類似"PACKAGE-VERSION.tar.gz"的 文件.PA
CKAGE和VERSION,是 我們在 configure.in中定義的 AM_INIT_AUTOM
AKE(PACKAGE, VERSION).
make distcheck
|
錯誤處理:
When try to configure an open source code, I get error like this :
configure: error: cannot find install-sh, install.sh, or shtool in “.” “./..” “./../..”
<pre>
</pre>
“Libtool library used but ‘LIBTOOL’ is undefined”
<pre>sudo apt-get install autoconf
sudo apt-get install automake
sudo apt-get install libtool
重新執行aclocal/autoheader</pre>
required file build/ltmain.sh' not found
$ automake --add-missing
build/ltmain.sh’ not found
....
configure.in:18: required file
….
解決方案(libtoolize配置即可):
$libtoolize –version
-libtoolize (GNU libtool) 1.4.2
…..
$libtoolize –automake –copy –debug –force