对于写window-c++的程序员来讲由IDE帮他们解决源代码的编译过程,可是针对linux-c/c++程序写一个makefile 确实也让人头痛
最近源码编译开源软件的时候认识了automake,今天就使用automake作了一个测试,编译个c++伪工程linux
Linux下automake软件编译与发布之多级目录结构的处理
多级目录结构的软件,通常是单个程序、库文件或模块放在各自的目录中。automake要求每一个目录都有本身的Makefile.am文件来编译各自目录下的代码。
在顶级的目录中,有一个Makefile.am文件,该文件经过SUBDIRS指明了这个目录下有多少个直接下级目录的代码须要编译。下级目录的Makefile.am也指明本身须要编译的下级目录。
经过这样的层层递归,从而完成多级目录结构的编译。
例子目录结构以下:
leicc
|src
||--main.cpp
||--main.h
||--global.h
||api
|||--api.h
|||--api.cpp
|||--app.h
|||--app.cpp
||logic
|||--user.h
|||--user.cpp
下面是编译步骤:
1.运行autoscan产生configure.scan
在顶级目录leicc下运行autoscan命令。产生configure.scan
2.编辑 mv configure.scan configure.in 而后编辑configure.in
将configure.scan更名成configure.in,而后修改以下:
# -*- Autoconf -*-
# Process this file with autoconf to produce a configure script.c++
AC_PREREQ([2.63])
AC_INIT([FULL-PACKAGE-NAME], [VERSION], [BUG-REPORT-ADDRESS])
AM_INIT_AUTOMAKE(main, v1.0) #软件包名称和版本号
AC_CONFIG_SRCDIR([src/main.cpp])
AC_CONFIG_HEADERS([config.h])程序员
# Checks for programs.
AC_PROG_CXX
AC_PROG_CC
#使用了静态库编译,须要此宏定义
AC_PROG_RANLIBapi
# Checks for libraries.app
# Checks for header files.
AC_CHECK_HEADERS([stdlib.h string.h])ide
# Checks for typedefs, structures, and compiler characteristics.测试
# Checks for library functions.
AC_FUNC_MALLOC
AC_CHECK_FUNCS([memset])
#须要生成的Makefile
AC_OUTPUT(Makefile src/Makefile src/api/Makefile src/app/Makefile)
3.运行aclocal和autoconf/autoheader
configure.in修改完后则前后执行aclocal和autoconf命令。
4.创建各个目录的Makefile.am文件
在顶级目录、src目录和api/logic目录下分别创建三个Makefile.am文件。内容分别以下:
顶级目录Makefile.am: ui
AUTOMAKE_OPTIONS=foreign
SUBDIRS=src #本目录的直接下级目录src须要编译
#EXTRA_DIST=doc/userguide #doc/userguide不须要编译,但要发布该文件。若是有多个文件,则用空格分开。
src目录下的Makefile.am:this
AUTOMAKE_OPTIONS=foreign
SUBDIRS=api logic #本目录的直接下级目录api须要编译
bin_PROGRAMS=main #本目录的文件编译成可执行文件main。若有多个,用空格分开。而后在下面分别写它们的SOURCE和LDADD。
main_SOURCES=main.cpp #编译main须要的源文件列表,若有多个,用空格分开。
main_LDADD=api/libapi.a logic/liblogic.a #编译main须要的库文件列表。若有多个,用空格分开。
api目录下的Makefile.amblog
AUTOMAKE_OPTIONS=foreign
noinst_LIBRARIES=libapi.a #本目录下的代码编译成libapi.a库。不须要发布。若是须要发布,则写成bin_LIBRARIES。注意,库的名称格式必需为 libxxx.a。由于编译静态库,configure.in须要定义AC_PROG_RANLIB宏。
noinst_HEADERS =api.h app.h #定义头文件
libapi_a_SOURCES=api.cpp app.cpp #编译libapi.a须要的源文件。注意将库名称中的'.'号改为'_'号。
logic目录下的Makefile.am
AUTOMAKE_OPTIONS=foreign
noinst_LIBRARIES=liblogic.a #本目录下的代码编译成libapi.a库。不须要发布。若是须要发布,则写成bin_LIBRARIES。注意,库的名称格式必需为 libxxx.a。由于编译静态库,configure.in须要定义AC_PROG_RANLIB宏。
noinst_HEADERS =user.h #定义头文件
liblogic_a_SOURCES=user.cpp #编译libapi.a须要的源文件。注意将库名称中的'.'号改为'_'号。
6.运行automake --add-missing 以上几个Makefile.am都书写完毕后,运行automake --add-missing。 7.运行./configure和make 上面步骤完成后,前后运行./configure和make完成编译。若是编译成功,运行make dist能够将全部文件打包成main-v1.0.tar.gz