1
Separate compilation Large programs are generally separated into multiple files, e.g. tuples.h, ray.h, ray.c, tuples.c main.c With several files, we can compile and link our program as usual using gcc -Wall ray.c tuples.c main.c When compiling in this manner produces a problem, we fix the problem and recompile. But, we ended up recompiling everything with gcc -Wall ray.c tuples.c main.c even if we had to make a very simple change to just one file. This is wasteful.

2
Separate compilation What we should do instead is separately compile source files to intermediate object files and then link them together So, for the files –ray.c –tuples.c –main.c We want to compile each piece separately and then link them together. When we just compile source code (without linking it together), it means that we take the.c files and generate intermediate object (.o) files.

3
Separate compilation To just compile source code, use the -c flag with the compiler... gcc -Wall -c tuples.c gcc -Wall -c ray.c gcc -Wall -c main.c This will generate the object files tuples.o, ray.o, and main.o Finally, to link the object files (.o) into an executable that we can run, we use the compiler again (although this time it will just pass the.o files on to the linking stage): gcc -Wall -o ray1 tuples.o ray.o main.o

4
The Unix “make” Utility Building a program consisting of multiple source modules: (tuples.c, ray.c, main.c) As we have just seen, one approach is to use gcc with the -c option to build tuples.o, ray.o, and main.o class/2100/examples ==> gcc -c -g tuples.c class/2100/examples ==> gcc -c -g ray.c class/2100/examples ==> gcc -c -g main.c The files tuples.o, ray.o, and main.o, are object files but they are not executable. Then gcc is used to invoke ld to link tuples.o, ray.o, main.o, and the standard C library files.

5
The Unix “make” Utility Building a program consisting of multiple source modules: (tuples.c, ray.c, main.c) class/2100/examples ==> gcc -o progx -g tuples.o ray.o main.o The file progx is an executable object file. An alternative approach is to perform compilation and linking all in one step: class/2100/examples ==> gcc -o progx -g tuples.c ray.c main.c The disadvantage of this method is that it is necessary to recompile all of the source files making up the program each time any one source module changes. The Unix make program is a handy utility that can be used to build things ranging from programs to documents.

6
make”Utility Helps you to build and manage projects Types of statements that can go in a makefile –macro definition – name that you define to represent a variable that may occur several times within the makefile –target definition – lists the target file, its required files, and commands to execute the required files in order to produce the target. –Suffix rules – indicate the relationship between target and source file suffixes (filename extensions). –Suffix declarations – lists of suffixes (file extensions) used in suffix rules

7
make”Utility target definition target: dependencies [tab] commands targets – labels that appear in column 1 and are followed by the ":" character. dependencies - a list of files following the name of the target. These are the files that are needed to make the target. The target "depends on these files." If any dependency is newer than the target, the target will be rebuilt. commands – specify the procedure for building the target. Each line must begin with the tab character, not spaces.

8
make”Utility For a project consisting of the files main.c, plane.c, vector.c and ray.h, the trivial way to compile the files and obtain an executable is gcc -Wall -g -o ray main.c plane.c vector.c A makefile for doing this would look like: ray: main.o plane.o vector.o gcc -Wall -g -o ray main.c plane.c vector.c In this example, target is ray. The dependencies are main.o, plane.o, and vector.o In order for make to execute correctly, it has to meet all the dependencies of ray. If main.o, plane.o, or vector.o is newer than ray, then make rebuilds ray

9
make”Utility - Running make on the command line There are different ways to run make. 1.make Looks in the current directory for a file named makefile or Makefile and runs the commands for the first target 2.make –f Looks in the current directory for a makefile with the given name and runs the commands of the first target. 3.make Looks for a file named makefile or Makefile and locates the target. This does not have to be the first target. It will run the commands for that target provided the dependencies are more recent than the target.

11
make”Utility Example ray: main.o plane.o vector.o gcc -Wall -g -o ray main.c plane.c vector.c clean: rm *.o *.err In this example, there are two targets: ray and clean The second target has no dependencies. The command make clean will remove all object files and all.err files.

12
Macros You want to use macros to make it easy to make changes. For example, if you use macros, it's easy to change the compiler and compiler options between g++ and cxx. It's easy to turn on and off debug options. Without macros, you would use a lot of search and replace. You use macros in makefiles for the same reason you define constants in programs. It's easier to update the files and make it more flexible.

13
Macros Predefined macro based names: $@ -- the current target’s full name $? -- a list of the target’s changed dependencies $< -- similar to $? But identifies a single file dependency and is used only in suffix rules $* -- the target file’s name without a suffix Another useful macro based facility permits one to change prefixes on the fly. The macro $(@:.o=.err) says use the target name but change the.o to.err.

14
Macro definition A makefile line with the following syntax MACRO-NAME = macro value. Invoked using the syntax $(MACRO-NAME) Result is that $(MACRO-NAME) is replaced by the current value of the macro. Examples OBJS = main.o vector.o list.o CC = gcc CFLAGS = -DDBG_PIX -DDBG_HIT

15
Makefile Comments in a makefile –Begin with # Continued lines –Lines in a makefile can be very long. For easier reading, a long line can be broken up into two or more lines by putting the \ character at the end of all but the last line. Example 1: ray: ray.o vector.o main.o ray.h vector.h gcc -o ray -Wall -g ray.o vector.o main.o -lm