|
CEG 333: Introduction to UnixPrabhaker Mateti
|
Syntax: make [-f Makefile] rule...
A makefile is a special text file that automates compiling a project. It is composed of rules, which depend on files (targets) to be compiled, commands to be run, and other even rules.
Once a makefile has been written, the make command
parses it and runs the necessary commands. By default,
make will read from the file in the current directory
named Makefile (with a capital "M"), and
uses the first rule as its goal. If invoked as make
RULENAME..., make instead takes its goal from the given
rules. An optional -f option specifies an alternate
filename.
make determines whether to execute a rule's
commands based on the modification times of its targets. So only
those files which have changed will be recompiled.
WARNING: a rule that depends on itself is a circular dependency. If make finds one, it stops with an error, since proceeding would create an infinite loop! This circular dependency may be direct or part of a chain with many links.
The format of a rule is:
rulename: name(s) of other rules this one depends on...
[command(s) to run after the dependencies]...
Any commands to be run for a rule must be indented with a tab. Not eight spaces, not two tabs, one tab.
The GNU Make program is smart enough to automatically generate targets for many common tasks. For example, if a target depends on "file.o", but no rule with that name is defined, make will look for "file.c", "file.cpp", or another source code file and attempt to create "file.o". The autogenerated target should usually be used, as it makes the Makefile much simpler.
make can figure out a basic command line on its own. If it is necessary to tell make to different compiler options (e.g., "-g" for programs that will be debugged), the programmer can define special variables in the Makefile:
| Variable | Use |
CXX |
The name of the C++ compiler. |
CXXFLAGS |
Options for the C++ compiler. |
Note: Although our make command can autogenerated
targets, some older versions of make can't. Often, the newer GNU
Make utility used in the lab is available under the name
gmake.
all: my_program log
my_program: program2.o program1.o
g++ -c -msse -mmmx program1.o program2.o -o my_program
log:
date >> log.txt
program2.o:
g++ -c -msse -mmmx -o program2.o program2.cpp
The first time this is run, make goes through the following steps:
On subsequent runs, make examines the output files (my_program, program1.o, etc), and only runs the relevant steps when the files have changed.
This Makefile is suitable for small, single directory projects. It can be modified to build any of this class's assignments.
CXXFLAGS = -g -Wall
OBJFILES = simDisk.o bitVector.o directory.o
PROJECT = P1
$(PROJECT): $(OBJFILES)
$(CXX) $(CXXFLAGS) -o $(PROJECT) $(OBJFILES)
$(OBJFILES): fs33types.h
indent:
indent -kr -i2 -pmt *.cpp *.h
archive: clean
( TOPDIR=`basename \`pwd\`` ; cd .. ; tar -czf $$TOPDIR-`date +%G%m%d%H%M`.tgz $$TOPDIR )
clean:
rm -fr *.o *~ *.out $(PROJECT) \\#*
CXX variable is never defined, so make
checks the system for a usable C++ compiler and finds
g++.$(PROJECT) target (the final executable)
isn't autogenerated, so CXXFLAGS need to be passed
explicitly.Several versions of this example Makefile have been discussed on the newsgroup. You may wish to read over some of the postings for more information on how it works.