The Makefile utility Motivation Small programs single file

  • Slides: 56
Download presentation
The Makefile utility

The Makefile utility

Motivation § Small programs single file § “Not so small” programs : – Many

Motivation § Small programs single file § “Not so small” programs : – Many lines of code – Multiple components – More than one programmer

Motivation – continued § Problems: – Long files are harder to manage (for both

Motivation – continued § Problems: – Long files are harder to manage (for both programmers and machines) – Every change requires long compilation – Many programmers can not modify the same file simultaneously – Division to components is desired

Motivation – continued § Solution : divide project to multiple files § Targets: –

Motivation – continued § Solution : divide project to multiple files § Targets: – Good division to components – Minimum compilation when something is changed – Easy maintenance of project structure, dependencies and creation

Project maintenance § Done in Unix by the Makefile mechanism § A makefile is

Project maintenance § Done in Unix by the Makefile mechanism § A makefile is a file (script) containing : – Project structure (files, dependencies) – Instructions for files creation § The make command reads a makefile, understands the project structure and makes up the executable § Note that the Makefile mechanism is not limited to C programs

Project structure § Project structure and dependencies can be represented as a DAG (=

Project structure § Project structure and dependencies can be represented as a DAG (= Directed Acyclic Graph) § Example : – Program contains 3 files – main. c. , sum. c, sum. h – sum. h included in both. c files – Executable should be the file sum

sum (exe) sum. o main. c sum. h sum. c sum. h

sum (exe) sum. o main. c sum. h sum. c sum. h

Make: Header Dependencies § What if … – Sensor. cc changes? – Sensor. h

Make: Header Dependencies § What if … – Sensor. cc changes? – Sensor. h changes? – Robot. h changes? § § Pattern rule ignores header dependencies! Requires unnecessary “make clean; make” Let gcc figure out the header dependencies for us! The –MM option produces make rules in a. d file which we can then include in the Makefile Sensor. h Sensor. cc Robot. h Robot. cc robotest. cc

makefile sum: main. o sum. o gcc –o sum main. o sum. o main.

makefile sum: main. o sum. o gcc –o sum main. o sum. o main. o: main. c sum. h gcc –c main. c sum. o: sum. c sum. h gcc –c sum. c

Rule syntax main. o: main. c sum. h gcc –c main. c Rule tab

Rule syntax main. o: main. c sum. h gcc –c main. c Rule tab dependency action

Equivalent makefiles §. o depends (by default) on corresponding. c file. Therefore, equivalent makefile

Equivalent makefiles §. o depends (by default) on corresponding. c file. Therefore, equivalent makefile is: sum: main. o sum. o gcc –o sum main. o sum. o main. o: sum. h gcc –c main. c sum. o: sum. h gcc –c sum. c

Equivalent makefiles - continued § We can compress identical dependencies and use built-in macros

Equivalent makefiles - continued § We can compress identical dependencies and use built-in macros to get another (shorter) equivalent makefile : sum: main. o sum. o gcc –o $@ main. o sum. o: sum. h gcc –c $*. c

make operation § Project dependencies tree is constructed § Target of first rule should

make operation § Project dependencies tree is constructed § Target of first rule should be created § We go down the tree to see if there is a target that should be recreated. This is the case when the target file is older than one of its dependencies § In this case we recreate the target file according to the action specified, on our way up the tree. Consequently, more files may need to be recreated § If something is changed, linking is usually necessary

make operation - continued § make operation ensures minimum compilation, when the project structure

make operation - continued § make operation ensures minimum compilation, when the project structure is written properly § Do not write something like: prog: main. c sum 1. c sum 2. c gcc –o prog main. c sum 1. c sum 2. c which requires compilation of all project when something is changed

Make operation - example File sum main. o sum. o main. c sum. h

Make operation - example File sum main. o sum. o main. c sum. h Last Modified 10: 03 09: 56 09: 35 10: 45 09: 14 08: 39

Make operation - example § Operations performed: gcc –c main. c gcc –o sum

Make operation - example § Operations performed: gcc –c main. c gcc –o sum main. o sum. o § main. o should be recompiled (main. c is newer). § Consequently, main. o is newer than sum and therefore sum should be recreated (by relinking).

Another makefile example # Makefile to compare sorting routines BASE = /home/blufox/base CC =

Another makefile example # Makefile to compare sorting routines BASE = /home/blufox/base CC = gcc CFLAGS = -O –Wall EFILE = $(BASE)/bin/compare_sorts INCLS = -I$(LOC)/include LIBS = $(LOC)/lib/g_lib. a $(LOC)/lib/h_lib. a LOC = /usr/local OBJS = main. o another_qsort. o compare. o quicksort. o chk_order. o $(EFILE): $(OBJS) @echo “linking …” @$(CC) $(CFLAGS) –o $@ $(OBJS) $(LIBS) $(OBJS): compare_sorts. h $(CC) $(CFLAGS) $(INCLS) –c $*. c # Clean intermediate files clean: rm *~ $(OBJS)

Example - continued § We can define multiple targets in a makefile § Target

Example - continued § We can define multiple targets in a makefile § Target clean – has an empty set of dependencies. Used to clean intermediate files. § make – Will create the compare_sorts executable § make clean – Will remove intermediate files

Passing parameters to makefile § We can pass parameters to a makefile by specifying

Passing parameters to makefile § We can pass parameters to a makefile by specifying them along with their values in the command line. § For example: make PAR 1=1 PAR 2=soft 1 will call the makefile with 2 parameters: PAR 1 is assigned the value “ 1” and PAR 2 is assigned the value “soft 1”. The same names should be used within the makefile to access these variables (using the usual “$(VAR_NAME)” syntax)

Passing parameters - continued § Note that assigning a value to a variable within

Passing parameters - continued § Note that assigning a value to a variable within the makefile overrides any value passed from the command line. § For example: command line : make PAR=1 in the makefile: PAR = 2 § PAR value within the makefile will be 2, overriding the value sent from the command line

Conditional statements § Simple conditional statements can be included in a makefile. § Usual

Conditional statements § Simple conditional statements can be included in a makefile. § Usual syntax is: ifeq (value 1, value 2) body of if else body of else endif

Conditional statements - example sum: main. o sum. o gcc –o sum main. o

Conditional statements - example sum: main. o sum. o gcc –o sum main. o sum. o main. o: main. c sum. h gcc –c main. c #deciding which file to compile to create sum. o ifeq ($(USE_SUM), 1) sum. o: sum 1. c sum. h gcc –c sum 1. c –o $@ else sum. o: sum 2. c sum. h gcc –c sum 2. c –o $@ endif

Make: Advanced Options § Text manipulation functions – $(patsubst pattern, replacement, text) – $(patsubst

Make: Advanced Options § Text manipulation functions – $(patsubst pattern, replacement, text) – $(patsubst %. o, %. cc, <list of objfiles>) § Pattern rules – Uses a pattern in the target with % as wildcard – Matched % can be used in dependencies as well – Simple Example: %. o : %. cc <tab>command … § Pattern rules with automatic variables – – $@ full target name $< first dependency $* string which matched % wildcard Advance Example: %. o : %. cc <tab>$(CC) $(CCFLAGS) –c $< $(INCPATHS)

Make: A Simple Example CC=g++ FLAGS=-g MASLAB_ROOT=maslab-software LIB_DIR=$(MASLAB_ROOT)/liborc INC_DIR=$(MASLAB_ROOT)/liborc LIBS=-lm –lpthread -lorc # #

Make: A Simple Example CC=g++ FLAGS=-g MASLAB_ROOT=maslab-software LIB_DIR=$(MASLAB_ROOT)/liborc INC_DIR=$(MASLAB_ROOT)/liborc LIBS=-lm –lpthread -lorc # # # Compiler to use Compile flags Maslab software root directory orc-related library directory orc-related include directory Library files all : helloworld. o : helloworld. cc $(CC) $(FLAGS) –c $*. cc –o $@ helloworld: helloworld. o $(CC) -o helloworld. o $(LIBS) clean: rm -f *. o helloworld

Make: Example Makefile MASLABROOT = /mnt/maslab/software/maslab-software-current #This is the list of places to look

Make: Example Makefile MASLABROOT = /mnt/maslab/software/maslab-software-current #This is the list of places to look for include files INCPATHS = -I$(MASLABROOT)/ libs/liborc -I$(MASLABROOT)/libs/libim -I$(MASLABROOT)/libs/libbotserver -I/opt/intel/ipp/include #This is the list of places to look for libraries LIBPATHS = -L$(MASLABROOT)/ libs/liborc -L$(MASLABROOT)/libs/libim -L$(MASLABROOT)/libs/libbotserver -L/opt/intel/ipp/sharedlib #This is the names of the libraries LIBS = -lippipx -lippcvpx -lim -lorc -lbotserver -lm -lpthread -ljpeg -lpng #This is the compiler to use CC = g++ # This is your c++ file extension (usually cc or cpp) CCEXT = cc

Make: Example Makefile (cont) CCFLAGS = -g -Wall # This rule builds everything. #

Make: Example Makefile (cont) CCFLAGS = -g -Wall # This rule builds everything. # programs in this list. all : robotest You should put the names of all your # This rule says how to turn any. cpp file into a. o file. %. o : %. $(CCEXT) $(CCFLAGS) -c $< $(INCPATHS) #-----------------------------------# robotest PROGRAM_NAME = robotest PROGRAM_OBJS = robotest. o Bump. Sensor. o Robot. o GLOBAL_OBJS += $(PROGRAM_OBJS) JUNK += $(PROGRAM_NAME): $(PROGRAM_OBJS) $(CC) $(PROGRAM_OBJS) -o $(PROGRAM_NAME) $(LIBS) $(LIBPATHS) chmod a+x $(PROGRAM_NAME)

Extending Example Makefile So to add a new executable program, simply cut and paste

Extending Example Makefile So to add a new executable program, simply cut and paste the robotest section and enter your own PROGRAM_NAME and PROGRAM_OBJS #-----------------------------------# Sensor Incremental Test PROGRAM_NAME = sensor-test PROGRAM_OBJS = sensor. t. o Bump. Sensor. o GLOBAL_OBJS += $(PROGRAM_OBJS) JUNK += $(PROGRAM_NAME): $(PROGRAM_OBJS) $(CC) $(PROGRAM_OBJS) -o $(PROGRAM_NAME) $(LIBS) $(LIBPATHS) chmod a+x $(PROGRAM_NAME)

Extending example Makefile DEPENDS += $(patsubst %. o, %. d, $(GLOBAL_OBJS)) JUNK += $(DEPENDS)

Extending example Makefile DEPENDS += $(patsubst %. o, %. d, $(GLOBAL_OBJS)) JUNK += $(DEPENDS) include $(DEPENDS) depend : $(DEPENDS) depend. $(CCEXT) = set -e; $(CC) $(CCFLAGS) -MM $(DEFS) $(INCPATHS) depend. filt = sed 's/($*). o[ : ]*/1. o $@ : /g' > $@; [ -s $@ ] || rm -f $@ %. d: %. $(CCEXT) $(depend. cc) $< | $(depend. filt) #=================================== # Miscellaneous Rules #-----------------------------------# This rule cleans your directory. You could also add commands here # to remove program files and any other files that should be cleaned clean: rm -f $(JUNK) *~ *. o core. [0 -9]* core

ANT: Another Nice Tool

ANT: Another Nice Tool

What is Ant? § Java-based Build tool from Apache § De facto standard for

What is Ant? § Java-based Build tool from Apache § De facto standard for building, packaging, and installing Java applications § Accomplishes same objectives that make does on Unix based systems § Files are written in XML

Why Ant? § Many claim. . That – Unlike makefiles, Ant files work cross

Why Ant? § Many claim. . That – Unlike makefiles, Ant files work cross platform - No need for multiple, complex makefiles depending on the operating system. - Tasks declared in platform independent way; Ant engine translates to OS specific commands. But still need to know (potentially) complex path/install data. So not as general as they claim § Easy to create own Ant “tasks”, in addition to core tasks

Installing Ant § Download Ant binary distribution from: http: //ant. apache. org/bindownload. cgi §

Installing Ant § Download Ant binary distribution from: http: //ant. apache. org/bindownload. cgi § Set ANT_HOME to where you installed Ant § Include $ANT_HOME/bin in PATH § Make sure JAVA_HOME is set to point to JDK

Running Ant § Type “ant” at the command line § Automatically looks for build.

Running Ant § Type “ant” at the command line § Automatically looks for build. xml file in current directory to run § Type “ant –buildfile. xml” to specify another build file to run.

Ant Output

Ant Output

Sample build. xml <project name="My. Project" default="dist" basedir=". "> <property name="src" location="src"/> <property name="build"

Sample build. xml <project name="My. Project" default="dist" basedir=". "> <property name="src" location="src"/> <property name="build" location="build"/> <property name="dist" location="dist"/> <target name="init"> <tstamp/> <mkdir dir="${build}"/> </target> <target name="compile" depends="init" > <javac srcdir="${src}" destdir="${build}"/> </target> <target name="dist" depends="compile" > <mkdir dir="${dist}/lib"/> <jar jarfile="${dist}/lib/My. Project-${DSTAMP}. jar" basedir="${build}"/> </target> <target name="clean" > <delete dir="${build}"/> <delete dir="${dist}"/> </target> </project>

Ant Overview: Project § Each build file contains exactly one project and at least

Ant Overview: Project § Each build file contains exactly one project and at least one target § Project tags specify the basic project attributes and have 3 properties: - name - default target - basedir § Example: <project name=“My. Project” default=“build” basedir=“. ”>

Ant Overview: Targets § § Target is a build module in Ant Each target

Ant Overview: Targets § § Target is a build module in Ant Each target contains task(s) for Ant to do One must be a project default Overall structure of targets: <target name="A"/> <target name="B" depends="A"/> <target name="C" depends="B"/> <target name="D" depends="C, B, A"/>

Ant Overview: Tasks § Each target comprises one or more tasks § Task is

Ant Overview: Tasks § Each target comprises one or more tasks § Task is a piece of executable Java code (e. g. javac, jar, etc) § Tasks do the actual “build” work in Ant § Ant has core (built in) tasks and the ability to create own tasks

Ant Overview: Tasks Example: <target name="prepare" depends="init“ > <mkdir dir="${build}" /> </target> <target name="build"

Ant Overview: Tasks Example: <target name="prepare" depends="init“ > <mkdir dir="${build}" /> </target> <target name="build" depends="copy" > <javac srcdir="src" destdir="${build}"> <include name="**/*. java" /> </javac> </target>

Ant Overview: Core Tasks § § § § javac – Runs the Java Compiler

Ant Overview: Core Tasks § § § § javac – Runs the Java Compiler java – Runs the Java Virtual Machine jar (and war) – Create JAR files mkdir – Makes a directory copy – Copies files to specified location delete – Deletes specified files cvs – Invokes CVS commands from Ant

Ant Overview: Writing Own Task § Create a Java class that extends org. apache.

Ant Overview: Writing Own Task § Create a Java class that extends org. apache. tools. ant. Task § For each attribute, write a setter method that is public void and takes a single argument § Write a public void execute() method, with no arguments, that throws a Build. Exception -- this method implements the task itself

Ant Overview: Properties § Special task for setting up build file properties: § Example:

Ant Overview: Properties § Special task for setting up build file properties: § Example: <property name=“src” value=“/home/src”/> § Can use ${src} anywhere in build file to denote /home/src § Ant provides access to all system properties as if defined by the <property> task

Ant Overview: Path Structures § Ant provides means to set various environment variables like

Ant Overview: Path Structures § Ant provides means to set various environment variables like PATH and CLASSPATH. § Example of setting CLASSPATH: <classpath> <pathelement path="${classpath}"/> <pathelement location="lib/helper. jar"/> </classpath>

Command Line Arguments § -buildfile – specify build file to use § targetname –

Command Line Arguments § -buildfile – specify build file to use § targetname – specify target to run (instead of running default) § -verbose, -quiet, -debug – Allows control over the logging information Ant outputs § -logger classname – Allows user to specify their own classes for logging Ant events

IDE Integration § Eclipse, Net. Beans, JBuilder, Visual. Age, and almost any other Java

IDE Integration § Eclipse, Net. Beans, JBuilder, Visual. Age, and almost any other Java IDE has Ant integration built-in to the system § Refer to each IDE’s documentation for how to use Ant with that IDE

Web Development with Ant § Tomcat comes with special Ant tasks to ease Web

Web Development with Ant § Tomcat comes with special Ant tasks to ease Web application development and deployment § Copy $TOMCAT_HOME/server/lib/catalina-ant. jar to $ANT_HOME/lib § Ant tasks for Tomcat: - install - reload - deploy - remove

Documentation/References § Good tutorial for makefiles http: //www. gnu. org/manual/make-3. 80/make. html § Good

Documentation/References § Good tutorial for makefiles http: //www. gnu. org/manual/make-3. 80/make. html § Good tutorial for cmakef http: //www. cmake. org/HTML/Documentation. html § ANT User Manual: http: //ant. apache. org/manual/index. html § Sun’s Web development tutorial (Ant and JSPs): http: //java. sun. com/webservices/docs/1. 2/tutorial/doc/Getting. Started 3. html

The real Problem § How do we handle platform specific issues? – Providing a

The real Problem § How do we handle platform specific issues? – Providing a different Makefile for each architecture – Using Autoconf, Automake and Libtool § The installer needs only – Bourne shell – C compilers – Make program

Some advantages when using GNU autotools § The installation of a program is straightforward:

Some advantages when using GNU autotools § The installation of a program is straightforward: . /configure; make install § This procedure checks for system parameters, libraries, location of programs, availability of functions and writes a Makefile §. /configure supports many options to overwrite defaults settings

GNU autoconf Source Code configure. ac (configure. in) aclocal autoscan autoconfigure. scan configure

GNU autoconf Source Code configure. ac (configure. in) aclocal autoscan autoconfigure. scan configure

GNU automake Makefile. am automake Makefile. in configure Makefile

GNU automake Makefile. am automake Makefile. in configure Makefile

configure. ac § dnl Comment … … § AC_INIT(main. c) § AM_INIT_AUTOMAKE(project_name, 1. 2.

configure. ac § dnl Comment … … § AC_INIT(main. c) § AM_INIT_AUTOMAKE(project_name, 1. 2. 8) § AM_PROG_LIBTOOL it supports libtool and shared libraries § AC_PROG_CC it locates the C (C++) compiler § AC_HEADER_STDC it checks for standard headers § AC_CHECK_HEADERS(sys/time. h /header. h) it checks for headers availability § AC_CHECK_LIB(crypto SSLeay_version) it checks for libraries availability § AC_CHECK_FUNCS(ctime) it checks for functions availability § AC_PROG_INSTALL it checks for BSD compatible install utility § AC_OUTPUT([Makefile]) (or AC_PROG_CXX)

Makefile. am § bin_PROGRAMS = foo /configure --prefix=… (default /usr/local) § foo_PROGRAMS=foo. c foo.

Makefile. am § bin_PROGRAMS = foo /configure --prefix=… (default /usr/local) § foo_PROGRAMS=foo. c foo. h § noist_PROGRAMS=test (make compiles, make install does nothing) § EXTRA_DIST=disclaimer. txt

Example § foo. c : #include <stdio. h> main() { printf(“Cum grano salisn"); }

Example § foo. c : #include <stdio. h> main() { printf(“Cum grano salisn"); } § Makefile. am : bin_PROGRAMS = foo_SOURCES = foo. c § configure. ac : AC_INIT(foo. c) AM_INIT_AUTOMAKE(latin_words, 0. 9) AC_PROG_CC AC_HEADER_STDC AC_PROG_INSTALL AC_OUTPUT([Makefile])

Summary § Source Code, configure. ac, Makefile. am § autoscan; aclocal; autoconf § Create

Summary § Source Code, configure. ac, Makefile. am § autoscan; aclocal; autoconf § Create NEWS README AUTHORS Change. Log § automake –add-missing §. /configure; make dist § Result: project_name-2. 10. tar. gz aclocal. m 4 autom 4 te-2. 53. cache Change. Log config. status configure. in COPYING install-sh Makefile. am missing NEWS README AUTHORS autoscan. log configure. scan INSTALL Makefile. in mkinstalldirs code. c

References § GNU Autoconf, Automake, and Libtool http: //sources. redhat. com/autobook/autobook_toc. html § GNU

References § GNU Autoconf, Automake, and Libtool http: //sources. redhat. com/autobook/autobook_toc. html § GNU Autoconf Manual http: //www. gnu. org/manual/autoconf § GNU Automake Manual http: //www. gnu. org/manual/automake § GNU Libtool Manual http: //www. gnu. org/manual/libtool § Learning the GNU development tools http: //autotoolset. sourceforge. net/tutorial. html § The GNU configure and build system http: //www. airs. com/ian/configure_toc. html § GNU macro processor (GNU m 4) http: //www. gnu. org/manual/m 4 -1. 4/m 4. html