\documentstyle [11pt]{article}

\title{Make - A Program Maintenance Utility}
\author{Rajappa Iyer\\Internet: banker@shakti.ernet.in\\UUCP: \dots!uunet!shakti!banker}

\parindent 0pt
\parskip 1.5pt

\begin{document}
\maketitle

\section{Introduction}

     Make is  an automatic  program maintenance  utility. It
     executes commands  specified in  makefile to update one
     or more targets.

     Make updates  a target only if its dependents are newer
     than the target. All prerequisite files of a target are
     added recursively to the list of targets. Missing files
     are deemed to be out-of-date.

\section{What is a Makefile?}

     A makefile is a plain text file containing one or
     more of the following:

\begin{itemize}

\item     dependencies

\item     inference rules

\item     macros

\item     comments

\end{itemize}

     Each  of   these   items   follow   certain   syntactic
     conventions which  are described later. Any line except
     a comment  line may  be continued  over more  than  one
     physical line  by appending the backslash character `$\backslash$'
     at the end of the line. Thus the two lines,

\begin{verbatim}
     This is one line
\end{verbatim}

     and

\begin{verbatim}
     This is \
     one line
\end{verbatim}

     are identical.  Note that  the backslash character must
     be the last character on the line.
     A comment line is terminated by a newline and cannot be
     continued by appending a backslash.

\subsection{Dependencies}

     Dependencies in a makefile are of the following form:

\begin{verbatim}
     target [target] :[:] [depend] [depend] [;commands]
     [<tab>commands]
\end{verbatim}

     where items  enclosed in  square brackets are optional.
     This informs  {\sl Make}\/ that  the items  on the left side of
     the colon  are dependent on the items on the right side
     of the  colon. The commands needed to update the target
     may also  be  specified---either  on  the  same  line
     prefixed by  a semi-colon  or on immediately subsequent
     lines prefixed by a tab. Note that the tab character is
     essential---{\sl Make}\/ will  complain if  it finds a command
     without a tab character prefix with the message:

\begin{verbatim}
     Make : syntax error near line %d, file %s.
\end{verbatim}

     If no depends are specified the target is assumed to be
     out of  date and  the associated  commands  are  always
     executed.

     If two colons are specified, then the target may appear
     as a  target in more than one dependency line each time
     followed by  two colons.  Normally, a  target may  only
     appear once  as a target in the makefile. For a double-
     colon dependency,  the target  is maintained up to date
     with respect to each set of depends.

     If no  commands are  specified, then  {\sl Make}\/ searches its
     internal database  for appropriate  commands to  update
     the target  and issues  them. If  no such  commands are
     found, {\sl Make}\/ aborts with the message

\begin{verbatim}
     Make : don't know how to make target.
\end{verbatim}

     The depends  of  a  target  may  themselves  appear  as
     targets in other dependency lines.

     Dependencies may  be specified  in any order whatsoever
     so long  as it  is not  cyclical---{\tt a} depends on {\tt b} which
     depends on {\tt c} which  in turn depends on {\tt a}. However, the
     target of  the first  dependency specified  becomes the
     default target to be updated.

     Following is an example makefile.

\begin{verbatim}
     foo : foo.o bar.o ugh.o
          cc foo.o bar.o ugh.o -o foo
     
     foo.o : foo.c
          cc -c foo.c
     
     bar.o : bar.c
          cc -c bar.c
     
     ugh.o : ugh.c
          cc -c ugh.c
\end{verbatim}

     In  this  case, {\tt foo}  becomes  the  default target to be
     updated. {\sl Make}\/  will first  ensure that {\tt foo.o}, {\tt bar.o}
     and {\tt ugh.o} are more recent than
     {\tt foo.c}, {\tt bar.c} and {\tt ugh.c}
     respectively and then ensure that {\tt foo} is more recent
     than {\tt foo.o}, {\tt bar.o} and {\tt ugh.o}.

\subsection{Inference rules}

     Note that  the commands  to update {\tt foo.o}, {\tt bar.o} and
     {\tt ugh.o}  with  respect  to  their  respective  depends,
     namely, {\tt foo.c},  {\tt bar.c} and {\tt ugh.c}
     are identical with only
     the filename  changed. {\sl Make}\/  provides  a  facility  for
     defining inference  rules which  can be used to specify
     transformations  for   related  files   with  different
     suffixes. To  illustrate, the above makefile could have
     been written as follows.

\begin{verbatim}
     .c.o :
          cc -c $<


     foo : foo.o bar.o ugh.o
          cc foo.o bar.o ugh.o -o foo
     
     foo.o : foo.c
     bar.o : bar.c
     ugh.o : ugh.c
\end{verbatim}

     The rule  to create a file with suffix {\tt .o} from a file
     with suffix  {\tt .c} is  specified as a dependency line with
     {\tt .c.o} as  a target  without any  depends. The commands
     associated with the dependency are applied to a {\tt .c} file
     to obtain  a {\tt .o}  file. The  symbol {\tt \$<}  expands to the
     appropriate  filename.   {\tt \$<}  is   a  special   sequence
     recognized by  {\sl Make}\/ and automatically substituted. More
     special sequences are enumerated in the section {\em Macros}.

     {\sl Make}\/ has  a default  set of such rules which it applies
     to update relevant targets. An inference rule specified
     in the  makefile will  override the  default  rule.  An
     explicit command  specified for  a target will override
     any applicable inference rules.

\subsection{Macros}

     {\sl Make}\/ supports  simple text-replacement  macros  in  the
     makefile. A macro definition is of the form:

\begin{verbatim}
     var=value
\end{verbatim}

     where whitespace surrounding the equal sign is ignored.

     Macro names  are case  sensitive. A  macro  can  appear
     anywhere in  the makefile  prefixed by  a dollar  (`\$')
     sign. Macro  names which are longer than one character,
     must be  delimited either  by parentheses  or by  curly
     braces.

     For example:

\begin{verbatim}
     OBJECTS=foo.o bar.o ugh.o


     foo : $(OBJECTS)
          cc $(OBJECTS) -o foo
\end{verbatim}

     Single character  macro names  need not be delimited by
     parentheses. Thus {\tt \$Z} is equivalent {\tt \$(Z)}
      or {\tt \$\{Z\}}. Use {\tt \$\$}
     to represent the dollar sign.

     {\sl Make}\/ supports  a  limited  form  of  text  substitution
     within macros. The general mechanism for using this is

\begin{verbatim}
     ${VAR:T=S}
\end{verbatim}

     This  will   expand  the   macro  {\tt VAR}  replacing  those
     occurrences of  the string  {\tt T} which immediately precede
     whitespace or  the end  of string  by string {\tt S}. This is
     primarily used to change suffixes as shown below:

\begin{verbatim}
     SOURCES=$(OBJECTS:.o=.c)
\end{verbatim}

     {\tt \$(SOURCES)} will now expand to {\tt foo.c bar.c ugh.c}.
     In addition  to user defined macros, {\sl Make}\/ also reserves
     a few  special macros  which are  evaluated only at the
     time of updating a target. These are:

\begin{itemize}
\item[{\tt \$*}]   basename of target
\item[{\tt \$<}]   full name of depend
\item[{\tt \$\char94}]   all depends
\item[{\tt \$?}]   all depends newer than target
\item[{\tt \$@}]   full name of target
\end{itemize}

     Of these macros, {\tt \$*}, {\tt \$<} and {\tt \$@}
     have alternative forms---when an upper case D or
     upper case F is appended to the
     macros, it  evaluates to  the directory  part for D and
     the  file  part  for  F.  Thus,  {\tt \$(@D)}  refers  to  the
     directory part of {\tt \$@}.

     These special  macros may  be used  only  in  inference
     rules and  commands  whereas  user-defined  macros  may
     appear anywhere.

\subsection{Dynamic dependency parameters}

     Make supports  a special  set of  parameters which have
     meaning only  on a  dependency  line,  namely  {\tt \$\$@}  and
     {\tt \$\$(@F)}. The  {\tt \$\$@} refers  to the  current ``thing'' to the
     left of  the colon  (which is  {\tt \$@}) while  {\tt \$\$(@F)} is the
     file part of {\tt \$\$@}. Thus, in the line

\begin{verbatim}
     foo.c : $$@,v
\end{verbatim}

     the dependency  is translated  at execution time to the
     string {\tt foo.c,v}.  This is useful in, say, checking out a
     large number of files at one time.


\begin{verbatim}
     SRCS=foo.c ugh.c bar.c


     $(SRCS) : $$@,v
          $(CO) $(COFLAGS) $<
\end{verbatim}
     The second  useful form  of the dependency parameter is
     {\tt \$\$(@F)}. It  represents  the  file  name  part
     of  {\tt \$\$@}.
     Suppose that  you wish  to maintain  a public directory
     from a  local private  one. The makefile in the private
     directory would look like.

\begin{verbatim}
     PUBDIR=/usr/public
     
     PUBLICS=$(PUBDIR)/foo $(PUBDIR)/bar $(PUBDIR)/ugh
     
     $(PUBLICS) : $$(@F)
          cp $< $@
\end{verbatim}

     This would  maintain the  public directory whenever any
     of the  relevant files  in the  private  directory  are
     changed.

\subsection{Comments}

     Comments can  appear anywhere  in the  makefile where a
     newline can appear. They are started by the character `\#' on
	 Unix and MS-DOS and by the character `\&' on VOS.
     Comments  are
     terminated by  the newline  character---this cannot be
     overridden.

\section{Special Targets}

     Special targets  are specified  in the  same manner  as
     real targets but without any associated commands. It is
     a syntax  error to  specify a  command with  a  special
     target. Some  of the  special targets expect depends to
     be specified  and some  don't. In  case of  the latter,
     depends, if specified, are ignored.

     The first character of any special target is the period
     character and  the target  name is  all  caps.  Special
     targets are never updated---they are used to modify the
     behavior of  {\sl Make}.  Following  is  a  list  of  special
     targets which may appear in a makefile.

\subsection{.DEFAULT}
     If a  file needs to be remade but there are no explicit
     commands  or  relevant  built-in  rules,  the  commands
     associated with  the  name  {\tt .DEFAULT}  are  used  if  it
     exists.

\subsection{.PHONY}
     The depends  of this target are considered phony---that
     is {\sl Make}\/  assumes that they do not exist and will always
     consider it  out of  date with  respect to its depends.
     This is useful for pseudo targets such as:

\begin{verbatim}
     .PHONY : all

     all : foo.pm bar.pm ugh.pm

     foo.pm : foo.o
     bar.pm : bar.o
     ugh.pm : ugh.o
\end{verbatim}

     {\sl Make}\/ will  not attempt  to find  {\tt all} and  always try to
     update {\tt foo.pm}, {\tt bar.pm} and {\tt ugh.pm}.

\subsection{.PRECIOUS}
     Usually, {\sl Make}\/  deletes all  the intermediate files that
     it creates  in the  process of updating a target before
     terminating. It  also deletes  the target  that  it  is
     updating if an error occurs while updating it. However,
     sometimes  it   may  be   desirable   to   retain   the
     intermediate files  and the  target file even on error.
     You may inform {\sl Make}\/ not to delete these files by making
     them the depends of this special target.

\subsection{.SILENT}
     Normally {\sl Make}\/  prints the  commands that it is about to
     issue on  the standard  output device  before  actually
     executing  it.   On  error,   it   prints   appropriate
     diagnostics and terminates. The presence of this target
     in  the  makefile  informs  {\sl Make}\/  to  perform  its  job
     silently---no commands  or diagnostics to be echoed to
     screen.

     This directive  has the same effect as the {\tt -s} switch on
     the command  line  (see  {\em Invocation}).  No  depends  are
     needed.

\subsection{.IGNORE}

     {\sl Make}\/ considers a command to have failed if it returns a
     non-zero exit status. When a command fails, {\sl Make}\/ prints
     an appropriate  diagnostic and terminates. The presence
     of this  special target  in the  makefile cause {\sl Make}\/ to
     ignore all  error returns from commands and continue as
     if everything succeeded.

     This directive  has the same effect as the {\tt -i} switch on
     the command  line  (see  {\em Invocation}).  No  depends  are
     needed.


\subsection{.SUFFIXES}
     Make can  make some  inferences about the prerequisites
     for a  target. For  example, it  ``knows''  that  {\tt foo.o}
     depends on  {\tt foo.c}. {\sl Make}\/  derives this knowledge from
     the special target {\tt .SUFFIXES}.

     The depends  of this  special target  inform {\sl Make}\/ about
     the prerequisite  suffixes for any file. To illustrate,
     consider the following example:

\begin{verbatim}
     .SUFFIXES : .o .c
\end{verbatim}

     This informs  {\sl Make}\/ that {\tt foo}\footnote{The null suffix
     is implicit} depends on {\tt foo.o} which
     depends on  {\tt foo.c}. Thus, the following dependencies are
     implicit and need not be specified in the makefile.

\begin{verbatim}
     foo : foo.o
     foo.o : foo.c
\end{verbatim}

     The ordering  of the  suffix list is important since it
     is  scanned   from  left   to  right  for  prerequisite
     suffixes.  When  searching  for  a  prerequisite  to  a
     target, {\sl Make}\/  searches for  a file with a suffix on the
     right of  the target's  suffixes. When  such a  file is
     found and  if there is a transformation rule for such a
     combination, {\sl Make}\/  transforms a file with one suffix to
     a file with another suffix.

     Make has  a default  suffix list  and a  default set of
     inference rules  which can be overridden or enriched in
     the makefile.

     The dependents  of {\tt .SUFFIXES}  directive in the makefile
     are added  to the  default list.  An empty  suffix list
     after {\tt .SUFFIXES}  clears the list. Thus, to create a new
     suffix list  specify {\tt .SUFFIXES}  with an  empty list and
     then specify the new list.

\subsection{.ABBREVIATIONS}
     This target  is applicable  to VOS  only. The depend of
     this target  is used as the abbreviations file. The set
     of abbreviations  defined in this file then supplements
     the current  set. All  commands  in  the  makefile  are
     expanded using  these abbreviations.  Note that  in the
     absence  of   any  {\tt .ABBREVIATIONS}   directive  in   the
     makefile, the  current set of abbreviations will remain
     active.

\subsection{.PROLOG}
     The commands  associated with  this target are executed
     before any processing is done. This is mainly useful in
     setting up  initial  conditions  (copying  some  files,
     creating directories etc.)


\subsection{.EPILOG}
     The commands  associated with  this target are executed
     after all  processing is done. Note that these commands
     are executed  only if  there were no errors encountered
     during the  {\sl Make}\/ process.  Useful for  cleaning up some
     intermediate files etc.

\section{Default Macros and Rules}

     Make defines  a set  of default  macros  and  inference
     rules. To  obtain this  in form  of a description file,
     type {\tt make  -p} (see  {\em Invocation}) and log
     the output in a file. We  shall consider  a few
      macros of  interest in this section.

\subsection{MAKE}
     This macro  is defined  to the name of the program - by
     default ``make''.  {\sl Make}\/  executes  lines  containing  the
     string {\tt \$(MAKE)}  or {\tt \$\{MAKE\}}  even when the
     {\tt -n} switch has
     been used  (see {\em Invocation}).  This macro may be used to
     change the  name of the make program without losing the
     significance associated with the macro name.

     This macro  is automatically defined by {\sl Make}\/ and can be
     overridden by an assignment in the makefile.

\subsection{MAKEFLAGS, MFLAGS}
     These two  macros define  the flags  that  reflect  the
     current switch settings in {\sl Make}. The {\tt MAKEFLAGS} macro is
     the same as {\tt MFLAGS} macro except that the option letters
     defined in  {\tt MFLAGS} have  the hyphen character prefixed.
     Thus the two lines in a makefile:

\begin{verbatim}
     $(MAKE) -$(MAKEFLAGS) target
\end{verbatim}

     and

\begin{verbatim}
     $(MAKE) $(MFLAGS) target
\end{verbatim}

     are identical.

     These two  macros are automatically defined by {\sl Make}\/ and
     can be overridden by assignments in the makefile.

\subsection{VPATH}
     This macro  is used  to specify alternative directories
     where {\sl Make}\/  can locate  target and  prerequisite files.
     The macro  should be assigned to a colon delimited list
     of directories  where {\sl Make}\/  should search for files not
     in current directory.

     {\sl Make}\/ prefixes  the directory name to the files found in
     one of  the directories  specified in  the {\tt VPATH} macro.
     For example,  consider  the  following  fragment  of  a
     makefile:

\begin{verbatim}
     VPATH=dir1:dir2:dir3

     foo : foo.o bar.o ugh.o
\end{verbatim}

     If {\sl Make}\/  does not  find, say,  {\tt bar.o} in  the  current
     directory, it  will search  the directories  {\tt dir1}, {\tt dir2}
     and {\tt dir3}  for the  file - in that order. If the file is
     found  in,   say,  {\tt dir2}   then  it   is  remembered  as
     {\tt dir2/bar.o}.

     This macro provides a powerful mechanism for supporting
     a system whose component files are spread over multiple
     directories.  However,   care  must   be  exercised  in
     defining rules  so as  to retain  consistency. Consider
     the following:

\begin{verbatim}
     VPATH=../include:../objects

     foo : foo.o
     foo.o : foo.c
\end{verbatim}

     Now suppose that {\tt foo.o} exists in {\tt ../objects} while {\tt foo.c}
     is in  current  directory.  In  this  case  {\tt foo.o}  is
     remembered as {\tt ../objects/foo.o}. If {\tt foo.c} is more recent
     than {\tt ../objects/foo.o},  then by  default the  following
     command will be issued:

\begin{verbatim}
     cc -c foo.c
\end{verbatim}

     However, {\sl Make}\/ will not think that {\tt foo.o}'s
     modification  time has changed since it ``remembers'' {\tt foo.o}
     as {\tt ../objects/foo.o} which has  not been  modified.
     Thus {\tt foo}  will not be updated  even though  it is out of
     date with  respect to {\tt foo.c}.  This  problem  can  be
     solved by  modifying the  rule to transform {\tt .c} files to
     {\tt .o} as follows:

\begin{verbatim}
     .c.o:
          $(CC) $(CFLAGS) $<
          -mv $(*F).o $@
\end{verbatim}

     This will  ensure that  the object  file created in the
     current directory  will be  moved  to  the  appropriate
     directory. Note that this transformation rule will work
     regardless of  which directory  {\sl Make}\/ is running in.

     The {\tt VPATH}  macro is not defined automatically by {\sl Make}\/ -
     it must be explicitly defined in the makefile.

\section{Invocation}

     The command line invocation of {\sl Make}\/ is as follows:

\begin{verbatim}
     make [-abdeiknpqrst] [-f makefile] [-c dir] [-o file]
          [var=value] [names]
\end{verbatim}

     where items  enclosed in  square brackets are optional.
     Switches to  {\sl Make}\/ are  single letters  preceded by  the
     hyphen  character.   They  may  appear  singly---each
     preceded by a hyphen, or they may be clubbed together---several
     characters  following a  hyphen. The  effect is
     the same  in either  cases. Thus,  {\tt make -ad  foo}  is
     identical to {\tt make -a -d foo}.

     The order in which the options appear is not important.
     However, some  options expect  arguments. In this case,
     the argument should immediately follow the option---any
     whitespace  in   between  the  option  letter  and  the
     argument is ignored. Thus, {\tt make -af makefile.foo} is not
     the same  as {\tt make  -fa makefile.foo}.  In the first case
     {\tt makefile.foo} is  considered to  be the  argument for {\tt -f}
     and the latter case {\tt a} is considered to be the argument.

     Option letters  are case-sensitive.  All switches  must
     appear before other arguments.

     The various options recognized by {\sl Make}\/ are:

\begin{itemize}
\item[--a]   Consider all  targets out  of date  regardless  of
          actual status.  Useful when  performing a complete
          rebuild of the system.

     \item[--b]   Backward compatibility  with older makefiles. Does
          nothing  and   is  present   only  for  historical
          reasons.

     \item[--c dir]    Change current  working directory so that {\sl dir}
          is  the   current  directory.  {\sl Make}\/  changes  the
          directory before  doing anything---even  reading
          makefiles. Useful  for recursive makes spread over
          different directories.

     \item[--d]   Debug mode.  In  this  mode  {\sl Make}\/  prints  verbose
          diagnostics  showing   the  complete   process  of
          updating  each   target.  Useful   for   debugging
          makefiles.

     \item[--e]   Override makefile definitions by variables defined
          in environment.  Normally environmental  variables
          (which are  treated like  macro  definitions)  are
          overridden by  macro definitions  in the  makefile
          (see {\em How  does Make  work ?}).  This is  applicable
          only in the Unix and MS-DOS environment and has no
          meaning in VOS.


     \item[--f file]   Reads  {\sl file}\/  as  the   makefile  instead  of
          defaults. If  file is  -- then  the standard  input
          device is read. If no {\tt -f} option is specified, then
          {\sl Make}\/  attempts   to   read   {\sl makefile},   {\sl Makefile},
          {\sl makefile,v} and {\sl Makefile,v} in that order (see {\em Using
          Make  with   SCAM}).  More  than  one  {\tt -f  makefile}
          argument pair may be specified.

     \item[--i]   Ignore  error  returns  from  commands  issued  to
          update a  target and treat it as having succeeded.
          Has the same effect as the presence of the special
          target {\tt .IGNORE} in the makefile.

     \item[--k]   Keep going.  On error, abandon current target, but
          continue making  other targets which do not depend
          on the target which could not be made.

     \item[--n]   Print, but do not execute, the commands that would
          be executed were the {\sl Make}\/ command actually issued.
          The  only   exception  is   that   command   lines
          containing the  {\tt \$(MAKE)} or  the {\tt \$\{MAKE\}} macro will
          be executed.  The {\sl Make}\/  thus invoked  will inherit
          the {\tt -n}  switch. This ensures that all the commands
          including those  that might be issued by sub-{\sl Make}s
          are printed.

     \item[--o file]   Consider {\sl file} as being really old. Useful for
          preventing unnecessary recompiles when a change in
          a prerequisite  file is of a nature which does not
          impact on  the targets  that  depend  on  it  (for
          example, adding a comment in an include file).

     \item[--p]   Print the database of internal rules and macros on
          the standard output device.

     \item[--q]   Question only if the target needs to be updated or
          not.  If   yes,  {\sl Make}\/   returns  a  non-zero  code
          otherwise, it returns a zero error code.

     \item[--r]   Do not use internal database of rules and macros.

     \item[--s]   Silent operation.  Do not print the commands to be
          executed and  diagnostics. Has  the same effect as
          the presence  of the special target {\tt .SILENT} in the
          makefile.

     \item[--t]   Touch all  targets which  are  out  of  date  with
          current date and time so that they appear updated.
          Useful to  prevent superfluous  updates which {\sl Make}
          is unable to recognize as such.
\end{itemize}

     Macro definitions  of the  form  {\tt var=value}  
     can also be specified on
     the command  line. This  macro definition overrides all
     other definitions.

     If names  are specified  on the command line, then {\sl Make}
     attempts  to   update  each   one  of  them  using  the
     dependency information  provided in the makefile. If no
     such information  is present or no makefile is present,
     {\sl Make}\/ uses  its internal  database to update the target.
     If names  are not  specified, then  {\sl Make}\/ picks  up  the
     default target  from the  makefile. It  is  illegal  to
     invoke {\sl Make}\/  without specifying  names on  the  command
     line when no makefile exists.

\section{How Does Make Work?}

     Upon invocation  of  {\sl Make}\/  the  following  sequence  of
     actions occurs.

\begin{itemize}
\item  {\sl Make}\/ reads the environmental variables {\tt MAKEFLAGS} and
       {\tt MFLAGS} to set the default flags. This is not
       applicable to the VOS environment.

\item The command line is then scanned for switches and
       macro definitions. The definitions are marked as non-
       resettable and they cannot be overridden. The macros
       {\tt MAKE}, {\tt MAKEFLAGS} and {\tt MFLAGS} are redefined to reflect
       current settings of switches and variables.

\item On Unix and MS-DOS all environmental variables that
       have been defined are read in. These definitions can
       be overridden by the definitions in makefile unless
       the {\tt -e} option is specified (see {\em Invocation}).

\item If the {\tt -r} option has not been specified, then the
       internal database of rules and macros are installed.

\item The makefile is now read for dependencies, macro
       definitions and inference rules. The files {\sl makefile},
       {\sl Makefile}, {\sl makefile,v} and {\sl Makefile,v} are tried in that
       order. If alternate makefiles have been specified
       using the {\tt -f} switch, then those files are read
       instead.
\end{itemize}

     The binding  of macros  is as  follows: default macros
     will  be   overridden  by  environmental  defines  (not
     applicable to  VOS). The  environmental defines will be
     overridden by  definitions in  makefile unless  the  {\tt -e}
     option is  specified. All definitions can be overridden
     by the command line.

     Default rules  can be  overridden by rules specified in
     the makefile.

     Once the dependencies, macro definitions and rules have
     been read  in, {\sl Make}\/  ensures that the targets are up to
     date with  respect to their depends by issuing commands
     that are either explicitly specified in the makefile or
     deduced from inference rules.

     Make first  prints the  command on  the standard output
     device, then executes it.

     The {\tt -s} option or the special target {\tt .SILENT} may be used
     to suppress the printing of all commands.
     Normally, an error terminates {\sl Make}. If the {\tt -i} option is
     present or the makefile has the entry {\tt .IGNORE:} then the
     error is  ignored. If  the {\tt -k}  option is  present, then
     work is  abandoned on  current entry,  but continued on
     other branches  of the  dependency tree  which  do  not
     depend on this file.
     
     The first one or two characters of the command may be {\tt -},
     {\tt @},  {\tt @-} or  {\tt -@}. If  {\tt @} is present,
     then the printing of
     the command  is suppressed.  If {\tt -}  is present  then the
     errors in that command are ignored. This may be used to
     correct for  ill-behaved programs  that return non-zero
     error codes inappropriately.
     
     On termination, abnormal or otherwise, {\sl Make}\/ deletes all
     intermediate files  unless  they  are  depends  of  the
     special target {\tt .PRECIOUS}.

\section{Using Make With SCAM}
     
     {\sl Make}\/ has  been designed  to work cooperatively with the
     {\sl Software Configuration  Administration  and  Management}\/
     system   ({\sl SCAM}).   It   recognizes   files   that   are
     administered by  {\sl SCAM}\/ and  issues checkout commands for
     needed files automatically.
     
     A {\tt SCAM} administered file is identified by its suffix---{\tt ,v}:
     a file  {\tt foo.c} when administered by {\sl SCAM}\/  is stored
     as  {\tt foo.c,v}.   Consider  the   following  fragment   of
     makefile.

\begin{verbatim}
     foo : foo.o bar.o ugh.o
\end{verbatim}

     Assume that  {\tt foo.c} is  being administered  by {\sl SCAM}\/   and
     that  no   copy  of  {\tt foo.c}  exists  either  in  current
     directory or in any one of the directories specified in
     the {\tt VPATH}.

     When {\sl Make}\/  attempts to  compare the  date time stamp of
     {\tt foo.o} with  that of  {\tt foo.c} (an inferable prerequisite
     for {\tt foo.o})  it does not find {\tt foo.c}. It then looks for
     the  file  {\tt foo.c,v}  in  the  current  directory,  in  a
     directory named  {\tt SCAM} in the current directory, in each
     one of  the directories  specified in  {\tt VPATH} and in the
     subdirectory  {\tt SCAM}  in  each  one  of  the  directories
     specified in  {\tt VPATH} in  that order.  That is, it checks
     for {\tt foo.c,v} as follows:

\begin{verbatim}
     foo.c,v
     SCAM/foo.c,v
     dir1/foo.c,v
     dir1/SCAM/foo.c,v
     dir2/foo.c,v
     dir2/SCAM/foo.c,v
     ...
\end{verbatim}

     When {\tt foo.c,v} is found, {\sl Make}\/ issues the command

\begin{verbatim}
     $(CO) $(COFLAGS) $<
\end{verbatim}

     to check out {\tt foo.c}. By default, {\tt CO} is defined to {\sl chkout}\/ 
     and {\tt COFLAGS} to {\tt -u} (no locking).

     When {\tt foo.c} has been checked out, {\sl Make}\/ compares the date
     and time  stamps of  {\tt foo.o} and {\tt foo.c} and performs the
     compilation if necessary.

     Note  that   {\sl Make}\/  will  only  check  out  those  files
     administered by  {\sl SCAM}\/  which are inferable prerequisites
     of the  current target.  If the  target depends on more
     than one file which is administered by {\sl SCAM}, then these
     files must be explicitly present in the dependency list
     for the  target. To  illustrate, consider the following
     makefile.

\begin{verbatim}
     foo : foo.o bar.o ugh.o
\end{verbatim}

     Suppose that all three files {\tt foo.c}, {\tt bar.c} and
     {\tt ugh.c} are
     administered by  {\sl SCAM}. Suppose also that {\tt foo.c} includes
     the file  {\tt foo.h} which is also administered by {\tt SCAM}. The
     above makefile  will cause {\tt foo.c}, {\tt bar.c} and {\tt ugh.c} to be
     checked out but not {\tt foo.h}. This is because {\tt foo.h} is not
     an  inferable   prerequisite  of   {\tt foo.o}.  Thus,  the
     following line must be added to the makefile:

\begin{verbatim}
     foo.o : foo.c foo.h
\end{verbatim}

     This will ensure correct operation of {\sl Make}.
     
     By setting  the macros  {\tt COFLAGS} appropriately, {\sl Make}\/ can
     be made  to checkout  only a  specified version  of the
     sources administered  by {\sl SCAM}.  For example, if release
     3.1 of all files are to be extracted, then just add the
     following line in the makefile.

\begin{verbatim}
     COFLAGS=-r 3.1
\end{verbatim}

     Makefiles can  be under  {\sl SCAM}\/  administration. {\sl Make}\/ will
     look for  files named  {\sl makefile,v} and {\sl Makefile,v} (if it
     does not  find {\sl makefile}\/ or {\sl Makefile}), check it out and
     read it before deleting it.

\section{Suggestions and Warnings}
     
     {\sl Make}\/ searches  for a file in current directory followed
     by all  the directories  defined by {\tt VPATH}. If a file is
     found in  one of the directories defined by {\tt VPATH}, then
     it remembers  the file  name with  the directory  name.
     This may  cause unexpected  behavior if a file with the
     same name exists in more than one directory.

     If a file {\tt foo.c} has a line

\begin{verbatim}
     #include "foo.h"
\end{verbatim}

     then the  object file  {\tt foo.o} depends  on  {\tt foo.h};  the
     source file  {\tt foo.c} does  not. If {\tt foo.h} is changed, then
     the object  file must  be recreated  and not the source
     file. The  following line  in the makefile will achieve
     the desired result.

\begin{verbatim}
     foo.o : foo.c foo.h
\end{verbatim}

     Due to  the nature  of the command processor on VOS and
     the shell on Unix, the {\tt cd} (change directory) command is
     ineffectual across  lines. Thus, the following fragment
     is incorrect:

\begin{verbatim}
     objects/foo.o : source/foo.c
          cd source
          cc foo.c
          mv foo.o ../objects/foo.o
          cd ..
\end{verbatim}

     It should be written as

\begin{verbatim}
     objects/foo.o : source/foo.c
          cd source; cc foo.c; \
          mv foo.o ../objects/foo.o; cd ..
\end{verbatim}

     Actually, the  last {\tt cd} is not needed since the
     current directory  will be  restored, once  the command
     line is  executed. The command can also be written much
     more compactly as follows:

\begin{verbatim}
     objects/foo.o : source/foo.c
          cc $<; mv $(@F) $@
\end{verbatim}

     If a  change is  a benign one, such as adding a comment
     in an  include file,  then the {\tt -t} (touch) option may be
     used  to   save  a   lot  of  time.  {\sl Make}\/  updates  the
     modification time  of the  affected  files  instead  of
     issuing superfluous compilations. This option should be
     used with  care since it subverts the intention of {\sl Make}
     and destroys all memory of the previous relationships.

\section{Bugs}
     Due to  certain subtle  dependency checks,  not all the
     commands that  are printed  when the  {\tt -n} switch is used
     will necessarily be executed. This is really a feature,
     not a bug.

     {\sl Make}\/ does not short-circuit transitive dependencies. If
     we specify the following two dependencies

\begin{verbatim}
     foo : foo.o
     foo.o : foo.c
\end{verbatim}

     and {\tt foo.o} does not exist then the transformation rule
     from {\tt foo.c} to {\tt foo} is not used even if it does exist.


\section{Conformance}

     Following features are ``non-standard'' in the current
     implementation of {\sl Make}. The ``standard'' is Sys V {\sl Make}.
     If an extension is present in either BSD 4.2 {\sl Make}\/ or
     SunOS {\sl Make}\/ or GNU 3.x {\sl Make}\/ then it is noted.

     Macro invocations may be nested---{\tt \$(m1\$(m2))} is legal.

     The environmental variable {\tt MFLAGS} is considered
     equivalent to {\tt MAKEFLAGS} with a hyphen prepended.
     (SunOS, BSD 4.2 and GNU 3.x)

     Support for special macro {\tt \$\char98} which expands to all the
     depends of the target. (GNU 3.x)

     Macro names may be delimited by curly braces as well
     as parens. (BSD 4.2 and GNU 3.x)

     Macro {\tt VPATH} defines a colon-separated list of directories
     where files may be found (if not in currnt directory).
     (BSD 4.2 and GNU 3.x)

     The depends of {\tt .PHONY} are always considered out of date.
     Useful for constructs like ``{\tt .PHONY : all}'' (GNU 3.x)

     Goals never come from include file. (GNU 3.x)

     Commands associated with special target {\tt .PROLOG} are
     executed prior to any {\sl Make}\/ process. (SunOS has {\tt .INIT})

     Commands associated with special target {\tt .EPILOG} are
     executed on successful completion of {\sl Make}. (SunOS has
     {\tt .DONE}).

     Dependency lines of the form of {\tt ../file.o : file.c} are
     supported---that is, a filename can start with the period
     character.

     No support for tilde suffixes and archives.

\end{document}
