• Usage of pmake


    Introduction

    Pmake is a program designed to simplify the maintenance of other programs. Its input is a list of specifications as to the files upon which programs and other files depend. mkdep, a program to construct Makefile dependency lists, is also included.

     

    This doc is not to introduce how to use pmake in detail. The goal of this doc is to introduce how to use the pmake templates which under /usr/share/mk . For more detail, refer to /usr/share/mk/bsd.README.

    Mk Template Files

    The following mk templates are very useful when you create your project. In this doc, we will deep into them.

    bsd.subdir.mk    - targets for building subdirectories

    bsd.lib.mk        - support for building libraries

    bsd.prog.mk     - building programs from source files

     

    Server Common Targets for three mks:

        all:

            build the program and its manual page

        clean:

            remove the program, any object files and the files a.out,

            Errs, errs, mklog, and ${PROG}.core.

        cleandir:

            remove all of the files removed by the target clean, as

            well as .depend, tags, and any manual pages.

        depend:

            make the dependencies for the source files, and store

            them in the file .depend.

        install:

            install the program and its manual pages; if the Makefile

            does not itself define the target install, the targets

            beforeinstall and afterinstall may also be used to cause

            actions immediately before and after the install target

            is executed.

        lint:

            run lint on the source files

        tags:

            create a tags file for the source files.

     

    1.         Target: all, clean. depend and install are often used in our project.

    2.         Using “.include ” to include any files into your makefile, such as “.include <bsd.subdir.mk>”, “../Makefile.env” and so on.

    3.         <bsd.lib.mk> and <bsd.prog.mk> include the file named "../Makefile.inc " if it exists, as well as the include file <bsd.man.mk>.

    4.         It's fairly difficult to make the BSD .mk files work when you're building multiple programs in a single directory. It's a lot easier split up the programs than to deal with the problem. In this doc we introduce two way to build multiple programs in a single directory..

    5.         The variable DESTDIR works when you want to install.  It's not set anywhere but will change the tree where the file gets installed. Like: pmake DESTDIR=/home/yourdir/install [-f Makefile] install

    Make Command

    Make command format:

    all: one two             # file one and two will be made first!

           Gcc ****           # multi shell commands can follow one target.

    Make –f Makefile.a  #The command will be execute in order. 

           Chmod 777 path

           Other command…..

     

    Note:

    1.         Any target can depend on some other files, such as *.c, *.cpp, *.o, lib and binary. These depended files will be made first before making the target.

    2.         One target can follow multi shell commands. These command swill be executed in order.

    bsd.subdir.mk

    Usage: Define which subdirs you want to make in variable SUBDIR.

    For all of the directories listed in the variable SUBDIR, the specified directory will be visited and the target made. The default targets are Server Common Targets.

    Example

    ===================================

    MYDIR= toolbox app    # internal variable

    SUBDIR= TestLib TestLib/demo ${MYDOR}

     

    .include <bsd.subdir.mk>

    # DO NOT DELETE

    ====================================

    bsd.lib.mk

    <bsd.lib.mk> has support for building libraries, such as *.a, *.so, *.po. Note: profiled libraries(*.po) are built by default.

    Common Variable

    LIB  à define the lib your want to build

    SRCS à lib’s source files

    CFLAGS  à define the include dir, which are used to search include files

     

    [ LDFLAGS à define the libs dir, which are used to search libs]

    [ LDADD  à define the libs you want to link/ Additional loader objects]

     

    NOMAN à not to build manual page

    INTERNALLIB à internal lib(??)

    NO_PROFILE à not to build *.po lib

    Example

    ====================================

    LIB = test

    SRCS = test.cc

     

    NOMAN=

    NO_PROFILE=

    INTERNALLIB=

     

    .include "../Makefile.env"

    CFLAGS+= -I../myutil

     

    .include <bsd.lib.mk>

    # DO NOT DELETE

    ====================================

    bsd.prog.mk

    The include file <bsd.prog.mk> handles building programs from one or more source files, along with their manual pages.

    Common Variable

    PROG à name of the program to build; If not supplied, nothing is built.

    PROG_CXX à using C++ lib; PROG_CXX overrides the value of PROG if PROG is also set.

    SRCS à lib’s source files

    PROGNAME à installation program name

     

    CFLAGS  à define the include dir, which are used to search include files

    LDFLAGS à define the libs dir, which are used to search libs

    LDADD  à define the libs you want to link/ Additional loader objects

    DPADD  à define additional dependencies for the program. Note: can’t build lib automatically!

     

    SUBDIR à A list of subdirectories that should be built as well. Like <bsd.subdir.mk>.

    Example

    Make one program:

    ====================================

    PROG=   unit-doe

    SRCS=   doeclient.cc TaskProtocol.pb.cc

     

    NOMAN=             # not need to make manual page.

    NEED_GBUFFER=     # include CFLAGS, LDFALGS and LDADD from “../Makfile.inc”

    NEED_SACP=

     

    CFLAGS= -Wall

     

    .include <bsd.prog.mk>

    ====================================

    Make multi programs way 1:

    ====================================

    PROG= doeserver

    SRCS= doeserver.cc ServerMixedApp.cc DoeTaskProcess.cc TasksOperation.cc TaskProtocol.pb.cc

     

    BINDIR= /app/bin

    BINDIRTOP= /bin

    DOECLIENT=unit-doe

    DOESERVER=doeserver

    DOEPROXY=doeproxy

     

    NOMAN=         # not need to make manual page.

    NEED_IPOPT=     # include CFLAGS, LDFALGS and LDADD “../Makfile.inc”

    NEED_LITHO=

    NEED_RESIST=

    NEED_DOE=

    NEED_SERVER_FRAME=

     

    all: updatelibs    # make updatelis before make default “doeserver”, then exec follow command

        ($(MAKE) -f Makefile.client ${.TARGET})

        ($(MAKE) -f Makefile.proxy ${.TARGET})

     

    updatelibs:     # make depend libs

        (cd http://www.cnblogs.com/util    && $(MAKE) libutility.a)

        (cd http://www.cnblogs.com/SACP    && $(MAKE) libSACP.a)

        (cd http://www.cnblogs.com/doe/helper     && $(MAKE))

        (cd ../lens              && $(MAKE) liblens.a)

     

    install:       # installation

        install -d -m 755 ${DESTDIR}$(BINDIR)

        install -m555 ${DOECLIENT} $(DESTDIR)$(BINDIR)

        install -m555 ${DOESERVER} $(DESTDIR)$(BINDIR)

        install -d -m 755 ${DESTDIR}$(BINDIRTOP)

    install -m555 ${DOEPROXY} $(DESTDIR)$(BINDIRTOP)

     

    .include <bsd.prog.mk>  # put before clean target, or the deoserver can’t be clean!

     

    clean:  cleanall

     

    cleanall:

        ($(MAKE) -f Makefile.client clean)

    ($(MAKE) -f Makefile.proxy clean)

     

    ====================================

    Make multi programs way 2:

    ====================================

    PROG= DoeUnitTest

    SRCS= DoeUnitTest.cc

     

    NOMAN =            # not need to make manual page.

    NEED_BRIONTEST =  # include CFLAGS, LDFALGS and LDADD “../Makfile.inc”

     

    TGT_LIST = DoeUnitTest sample1_unittest sample2_unittest  # DoeUnitTest will be made by default, even if it don’t list here.

     

    all: updatelibs $(TGT_LIST)   # define all target we want to make.

     

    clean:

        rm -f *.o $(TGT_LIST)

     

    updatelibs:      # make depend libs

        (cd ../    && $(MAKE))

     

    sample1_unittest : sample1.o sample1_unittest.o  # *.o will be made by default.

        ${CXX} ${CFLAGS} $(LDFLAGS) -o ${.TARGET} sample1.o sample1_unittest.o ${LDADD}

     

    sample2_unittest : sample2_unittest.o

        ${CXX} ${CFLAGS} $(LDFLAGS) -o ${.TARGET} sample2_unittest.o ${LDADD}

     

    .include <http://www.cnblogs.com/Makefile.env>

    .include <bsd.prog.mk>

     

    ====================================

    Make lib and programs:

    ====================================

    LIB= retrieval     # default make target

    SRCS= PupilRetrieval.cpp PupilRetrievalFrameStacks.cpp

     

    NOMAN =       # not need to make manual page.

    INTERNALLIB =

     

    NEED_RENDER=   # include CFLAGS, LDFALGS and LDADD “../Makfile.inc”

    NEED_UTIL=

    NEED_RESIST=

     

    TGT_LIST = asmlpupiltool   # define targets will be made

     

    all: libretrieval.a asmlpupiltool

     

    clean:

        rm -f *.o $(TGT_LIST) libretrieval.a

     

    install:

        @(install -m 555 asmlpupiltool ${DESTDIR}/app/bin/)

     

    .include <bsd.lib.mk>

     

    LDADD := -lfftw3f ${LDADD} -lodbc -lfetch -lgsl -llapack -lblas -lgslcblas -lexpat -lg2c -lstdc++ -lm

     

    asmlpupiltool: asmlpupiltool.o

        ${CXX} ${LDFLAGS} -o ${.TARGET} asmlpupiltool.o ${LDADD}

     

    ====================================

    Makefile Env File

    In a large project, we have to deal with muitl-platform, all kinds of third party lib and internal libs. Thus we can define some common make env variables in a file, other makefile only need to include the env file to load all env variables.

     

    Example

    OS Env

    ====================================

    OSTYPE!= uname –s        # get OS, such as Linux, Sun, FreeBSD and so on.

     

    .if ${OSTYPE} == "Linux"   # condition compile

    SUBDIR+= tacloader tacmanager tacshlib tacutil leafutilsampler tacutilsampler

    SUBDIR+= vspgen smo flaremapgen sim doeserver

    .endif

    =======================================

     

    Third Party Env

    =======================================

    .ifdef NEED_SERVER_FRAME    # define compiler macro

    NEED_SACP=     # enable compiler macro control variable, the macro must be defined after

    NEED_GBUFFER=         

    CFLAGS+= -I${APP}/comm.    # add additional include path

    LDFLAGS+= -L${APP}/comm

    LDADD+= -lcomm

    .endif

     

    .ifdef NEED_SACP    #these code must define before “LDADD+= -lutility…”. See Note 4).

    CFLAGS+= -I${TOPDIR}/SACP

    LDFLAGS+= -L${TOPDIR}/SACP

    LDADD+=  -lSACP

    .endif

     

    #============= NOTE: define NEED_XXXX above this line ============

    # Because our lib will depend on some third party lib and utility lib!

    CFLAGS+= -I${UTIL}

    LDFLAGS+= -L${UTIL} -L${THIRD_PARTY}/opt

    LDADD+= -lutility -Wl,-Bstatic -larpack -Wl,-Bdynamic -lcrypto -ltiff -ljpeg -lexpat -lpam -lopt

    .ifdef NEED_GBUFFER    # third party lib should be put after our libs.

    CFLAGS+= -I${PROTOBUF_DIR}/include

    LDFLAGS+= -L${PROTOBUF_DIR}/lib

    LDADD+=  -Wl,-Bstatic -lprotobuf -Wl,-Bdynamic

    .endif

    Note:

    1)      General speaking, the env file will be included by other makefile automatically or manually.

    2)      Make tool interpret all kinds of variables in order. It means that you should define variable before you use it. Thus, you should define macro control variable before the macro body.

    3)      CFLAGS, LDFLAGS and LDADD will be used in many places. Note: add first display first!

    4)      Gcc/g++ depend on the order of libs. Only the former libs can depend on latter libs. Thus, when you define the env file, you must pay attention on the order of libs.

    5)      If some libs are circular reference, they must be put between -Wl,--start-group and -Wl,--end-group.

    6)      –lutility will link libutility.a or libutility.so, *.so first. If you want to enforce to link lib statically, please use -Wl,-Bstatic to do that. Put these lib you want to link statically after -Wl,-Bstatic and don’t forget to put -Wl,-Bdynamic to recover to link dynamically.

  • 相关阅读:
    ubuntu 用shell脚本实现将当前文件夹下全部文件夹中的某一类文件复制到同一文件夹下
    读书笔记-2java虚拟机的可达性算法与finalize方法
    find the longest of the shortest (hdu 1595 SPFA+枚举)
    杭电 2176 取(m堆)石子游戏(博弈)
    MVC框架的优缺点
    Wireshark-TCP协议分析(包结构以及连接的建立和释放)
    Ubuntu安装教程--Win7系统中含100M保留分区
    eclipse新建android项目出现非常多错误
    关于简单的加密和解密算法
    在一台server上部署多个Tomcat
  • 原文地址:https://www.cnblogs.com/zhenjing/p/2021779.html
Copyright © 2020-2023  润新知