jmake(1)

NAME

   jmake - a generic makefile builder

SYNOPSIS

   jmake [ cpp options ]

DESCRIPTION

   Jmake  builds a makefile out of a rather high level description held in
   a Jmakefile file. The generated file is a  Makefile.SH  rather  than  a
   simple makefile, which means it is ready to be used in conjonction with
   metaconfig.  In  particular,  parameters  such  as  "where  to  install
   executables" will be automatically determined by Configure and only the
   needed parameters will be taken into account.

   To use jmake you have to write a Jmakefile first, which  describes  the
   way  things  are  to be built. Your Jmakefile will be included inside a
   generic template through the C pre-processor.  This means you  may  use
   the  usual  C  /**/  comments,  but  not  the  shell # comments.  The C
   comments will  not  appear  in  the  generated  Makefile.SH  but  lines
   starting  with ;# will finally appear as shell comments. If you have to
   write the string /* in the  generated  Makefile.SH  then  you  have  to
   escape  it  (otherwise  jmake  will  think  of  it  as the start of a C
   comment). Simply put a # in front of the *, as in /#*.

   You have a set of macros at your disposal, and  all  these  macros  are
   listed in the Index file, along with the piece of code they will expand
   to. Usually, a Jmakefile is fairly small and thus  easier  to  maintain
   than  a  huge  Makefile.   Some internal powerful commands allow you to
   write portable makefiles easily, without having to spend many  efforts,
   because someone else already did the job for you :-).

   When  you  want to generate your makefile, you usually do not run jmake
   but use the jmkmf script which is a wrapper and will invoke jmake  with
   the correct options.

   All  the  knowledge  of  jmake  is  held  in  two  files:  the template
   Jmake.tmpl and the macro definition file Jmake.rules.  The  first  file
   includes  the  second,  along  with  the  Jmakefile.   It  is sometimes
   necessary to know how things works to be able to correctly use all  the
   features  provided.  For instance, you may have to write your own rules
   for a specific project. Although you cannot  overwrite  the  predefined
   rules, you can extent the Jmake.rules file or simply add your macros in
   your Jmakefile.  You may also use #include statements when you want  to
   share these macros and do not want to duplicate the code.

   The syntax in Jmake.rules is not elegant at all, but:

   -      It is easy to parse (like sendmail.cf or troff files).
   -      The rules are not supposed to change very often.
   -      It is simple enough to be mastered in five minutes. :-)

          Here is a small description:

   1)     To deal with various cpp implementations:

          *      Final  @!\  means:  end  of line, next line starts at the
                 left margin.
          *      Final @@\ means: end of line, next line is to be indented
                 by one tab.

          There  should  always  be  one  of @!\ or @@\ at the end of each
          line.  The only exception is for macros that are to be  used  as
          part  of  a  rule body (e.g. RemoveTargetProgram). In that case,
          the first line (which holds  the  #define)  should  end  with  a
          single backslash.

   2)     Symbol definitions:

          *      >SYMBOL: defines the symbol.
          *      ?SYMBOL:<text>: keeps <text> iff SYMBOL is defined.
          *      %SYMBOL:<text>: keeps <text> iff SYMBOL is not defined.

          The ?SYM can be nested (logical AND), as in:

               ?SYMBOL:%TOKEN:text

          which  will  keep text if SYMBOL is defined and TOKEN undefined.
          To implement a logical OR, see below.

   3)     Makefile target tests:

          *      ?target?:<text>: keeps <test> iff target is defined.
          *      %target%:<text>: keeps <test> iff target is not defined.

                 A makefile target is defined as a standalone target,  for
                 instance  the depend.local target, which would be defined
                 as:

                      depend.local:

                 Also note that it is only valid for  targets  defined  so
                 far  in  the  generated  makefile.  It is not a predicate
                 that can be used to test for targets that will eventually
                 be defined later on in the generation.

   4)     Commands:

          Commands  can be passed to jmake. They start with a leading '|'.
          Available commands are:

          *      |suffix <sx>: adds <sx> to the  .SUFFIXES:  list  in  the
                 makefile.

          *      |rule:<text>: adds <text> to the building rule section.

          *      |rule: <text>: same as before, with a leading tab.

          *      |skip:  skips  text until a line starting with '-skip' is
                 found.

          *      |subst: begins section where lines  will  be  subject  to
                 variable  substitution,  until  '-subst'  is found.  This
                 means that when the Makefile.SH is run, all instances  of
                 $var  within the subst section will be substituted by the
                 shell.

          *      |shell: emits section until matching  '-shell'  as-is  in
                 the generated Makefile.SH.  This can be useful to prepare
                 |case  sections.   It  is  not  allowed  to  nest   shell
                 sections.

          *      |case:  this command must be followed by a shell variable
                 name (without its leading  '$'  sign)  and  a  case-style
                 pattern,  for  instance  the string "var in f*".  It will
                 generate the corresponding "case" test in the Makefile.SH
                 on  the  "$var"  value and only if this test is true will
                 the section until the matching '-case'  be  generated  in
                 the  Makefile when Makefile.SH is run.  It is possible to
                 nest case sections freely.

          *      |expand <pattern>:  expand  lines  until  '-expand'  with
                 <pattern>. A complete example is shown below.

          *      |once <symbol>: text up to '-once' appears only the first
                 time.

          The '|' commands cannot be nested, unless otherwise  noted.   In
          particular,  due  to  the  simple implementation of |skip, it is
          impossible to put |skip inside a skipped part. However, a  |once
          section  may  have  |skip sections.  It is allowed to nest |case
          sections at will.

          Here is a way to implement a logical OR:

               /* Implements SYMBOL or not TOKEN */
               ?SYMBOL:text        /* Keeps text if SYMBOL */
               %SYMBOL:|skip
                    %TOKEN:text         /* Keeps text if not TOKEN */
               -skip

          Actually, this is ugly, because the text has  to  appear  twice.
          Fortunately, I did not use that construct. :-)

          Indeed,  as  you  have  surely  already guessed, the best way to
          implement a logical OR is to use De Morgan's Law:

               not (p or q) <=> not p and not q

               /* Implements SYMBOL or not TOKEN (attempt #2) */
               %SYMBOL:?TOKEN:|skip
               text                     /* If SYMBOL or not TOKEN */
               -skip

          Who said they didn't care about logic? ;-)

          Expansion is done with the expand command.  It has been provided
          to  avoid some cumbersome writings in makefiles when you have to
          repeat some silly lines that only  differ  in  file  names,  for
          instance.  Let's look at an example first:

               |expand a!foo bar! b!yes no!
               !a::
                    echo !a, !b
               -expand

          Then  two rules will be printed, and the values of (a,b) for the
          first  will  be  (foo,  yes),  for   the   second   (bar,   no).
          Substitution  is controled by the '!' character.  If the word to
          be substituted is part  of  another  one,  detach  with  the  ^^
          construct  as in:  !b^^c.  It is possible to use Makefile macros
          in the <pattern>, and they will be expanded by jmake.   If  this
          is  not  what  you  want,  escape  the first '$' sign (this is a
          Makefile escape, i.e. you must double the '$',  not  precede  it
          with a backslash). A // stands for the null substitution value.
          The  ^^^ construct behaves like ^^, i.e. it is stripped out, but
          it also removes any following white space after the ^^^.  If you
          prepend  something  to a macro argument, and that macro argument
          was written with spaces  before  it,  then  this  will  let  you
          concatenate something right before that argument's final value.

          Here  is another example which shows how the macro Expand can be
          used.  It is defined in Jmake.rules as:

               #define Expand(rule, pattern) @!\
               |expand pattern @!\
               rule @!\
               -expand

          So we can write in the Jmakefile:

               |skip
               A = foo bar
               -skip

               #define Rule @!\
               $(DIR)/!a^^.o: !a^^.o @@\
                    $(CC) -c !a^^.c @@\
                    $(MV) !a^^.o $(DIR)

               Expand(Rule, a!$(A)!)

          which will generate in Makefile.SH:

               $(DIR)/foo.o: foo.o
                    $(CC) -c foo.c
                    $(MV) foo.o $(DIR)

               $(DIR)/bar.o: bar.o
                    $(CC) -c bar.c
                    $(MV) bar.o $$(DIR)

          The 'A' declaration has been surrounded by skip, so that it does
          not  appear  in  the generated Makefile.SH, but it will be taken
          into account by jmake for the substitution in the pattern.

          The number of expansions is determined by the number of possible
          values  for  the  first parameter. If other parameters have less
          substitution values, they will get void ones.

          It is possible to  add  a  regular  expression  at  the  end  of
          '-expand'.  This  regular  expression  will  be removed from the
          final set of expansion at the end  of  each  line.  It  is  also
          possible  to do substitutions in the expanded item, by using the
          syntax (if 'f' is the expanded variable)  !f:<p>=<q>  where  <p>
          and  <q>  are  two  regular  expressions  (without spaces).  The
          pattern <p> will be replaced by the pattern <q> (only the  first
          occurrence will be replaced).

          Finally,  you  may  refer  in  the expanded section to variables
          whose value is computed via another expansion,  which  makes  it
          easy to define generic Jmakefiles.

          Example:

               SRC = foo.c bar.c
               OBJ = \
               |expand f!$(SRC)!
                    !f:\.c=\.o \
               -expand \\
               INC = \
               |expand f!$(OBJ)!
                    !f:\.o=\.h \
               -expand \\

          which will generate in Makefile.SH:

               SRC = foo.c bar.c
               OBJ = \
                    foo.o \
                    bar.o
               INC = \
                    foo.h \
                    bar.h

          Do  not  forget  to  protect  special characters in your regular
          expressions such as backslash, point, etc...

          The once command is tagged with a name. The first time the  name
          appears,  the  once  construct  is  ignored  and  the text up to
          '-once' will be copied in the generated  Makefile.SH.   However,
          future  occurrences  of the same name will be ignored (once will
          behave like skip).

          Example:

               |once this_is_a_name
               <text>
               -once

          The shell command can be used to generate a  shell  fragment  in
          the  Makefile.SH.   For  instance,  the following section in the
          Jmakefile:

               |shell
               case "$d_usegtk1" in
               define) glib=1; gtk=1;;
               esac
               -shell

          will cause the  generation  of  the  enclosed  fragment  in  the
          Makefile.SH  to compute the values of the glib and gtk variables
          based on the configuration variable  d_usegtk1  set  by  running
          Configure.

          In  turn,  this  can  be  used  in  subsequent  case sections to
          activate parts of the Makefile only when building for GTK1 using
          glib-1.x:

               |case glib in 1
               display:
                    echo "Building for glib-1.x"
               -case

          This   section   will   generate  something  like  this  in  the
          Makefile.SH:

               !NO!SUBS!
               case "$glib" in
               1)
                    $spitshell >>Makefile <<'!NO!SUBS!'
               display:
                    echo "Building for glib-1.x"
               !NO!SUBS!
                    ;;
               esac
               $spitshell >>Makefile <<'!NO!SUBS!'

          And when running Makefile.SH, the "display" rule above will only
          appear  when  building  for  glib-1.x.   The  form  of the final
          Makefile can  therefore  depend  on  the  configuration  options
          chosen when Configure was run.

   5)     Initializations:

          *      +<line>:  Puts  the  whole  line  in  the  initialization
                 section.
          *      ++SYMBOL <value>: Adds <value> to the SYMBOL macro.

   6)     User-defined variables:

          The user may define CFLAGS, LDFLAGS  or  DPFLAGS  as  additional
          flags  to  be  used  in  C  compilation, linking phase or depend
          target. It is thus possible to add some extra flags such  as  -I
          or libraries for Makefiles in specific sub-directories.

AUTHOR

   Raphael Manfredi <[email protected]>

FILES

   Jmakefile           High level description of Makefile.SH
   Jmake.rules         File holding the macro definitions
   Jmake.tmpl          Template used to mould Makefile.SH

BUGS

   On  systems  whose  cpp  reduces  multiple  tabs and spaces to a single
   space, jmake attempts to  put  back  any  necessary  tabs  (which  make
   expects  in  front  of rules) but does not properly formats the body of
   the rule itself.

   There is a bootstraping problem when creating  the  first  Makefile.SH,
   because  you  cannot  run  it  through  a shell until there is a decent
   Configure script, but you  can't  run  metaconfig  before  there  is  a
   Makefile.SH or some needed symbols will not be defined.

SEE ALSO

   jmkmf(1), metaconfig(1).

                                  ram                             JMAKE(1)



Opportunity


Personal Opportunity - Free software gives you access to billions of dollars of software at no cost. Use this software for your business, personal use or to develop a profitable skill. Access to source code provides access to a level of capabilities/information that companies protect though copyrights. Open source is a core component of the Internet and it is available to you. Leverage the billions of dollars in resources and capabilities to build a career, establish a business or change the world. The potential is endless for those who understand the opportunity.

Business Opportunity - Goldman Sachs, IBM and countless large corporations are leveraging open source to reduce costs, develop products and increase their bottom lines. Learn what these companies know about open source and how open source can give you the advantage.


Free Software


Free Software provides computer programs and capabilities at no cost but more importantly, it provides the freedom to run, edit, contribute to, and share the software. The importance of free software is a matter of access, not price. Software at no cost is a benefit but ownership rights to the software and source code is far more significant.

Free Office Software - The Libre Office suite provides top desktop productivity tools for free. This includes, a word processor, spreadsheet, presentation engine, drawing and flowcharting, database and math applications. Libre Office is available for Linux or Windows.


Free Books


The Free Books Library is a collection of thousands of the most popular public domain books in an online readable format. The collection includes great classical literature and more recent works where the U.S. copyright has expired. These books are yours to read and use without restrictions.

Source Code - Want to change a program or know how it works? Open Source provides the source code for its programs so that anyone can use, modify or learn how to write those programs themselves. Visit the GNU source code repositories to download the source.


Education


Study at Harvard, Stanford or MIT - Open edX provides free online courses from Harvard, MIT, Columbia, UC Berkeley and other top Universities. Hundreds of courses for almost all major subjects and course levels. Open edx also offers some paid courses and selected certifications.

Linux Manual Pages - A man or manual page is a form of software documentation found on Linux/Unix operating systems. Topics covered include computer programs (including library and system calls), formal standards and conventions, and even abstract concepts.