OnWorks favicon

jmake - Online in the Cloud

Run jmake in OnWorks free hosting provider over Ubuntu Online, Fedora Online, Windows online emulator or MAC OS online emulator

This is the command jmake that can be run in the OnWorks free hosting provider using one of our multiple free online workstations such as Ubuntu Online, Fedora Online, Windows online emulator or MAC OS online emulator



jmake - a generic makefile builder


jmake [ cpp options ]


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:


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:


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

· |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 */
%TOKEN:text /* Keeps text if not TOKEN */

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) */
text /* If SYMBOL or not TOKEN */

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!
echo !a, !b

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 @!\

So we can write in the Jmakefile:

A = foo bar

#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.


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 \
INC = \
foo.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).


|once this_is_a_name

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

case "$d_usegtk1" in
define) glib=1; gtk=1;;

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
echo "Building for glib-1.x"

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

case "$glib" in
$spitshell >>Makefile <<'!NO!SUBS!'
echo "Building for glib-1.x"
$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.

Use jmake online using onworks.net services

Free Servers & Workstations

Download Windows & Linux apps

  • 1
    Phaser is a fast, free, and fun open
    source HTML5 game framework that offers
    WebGL and Canvas rendering across
    desktop and mobile web browsers. Games
    can be co...
    Download Phaser
  • 2
    VASSAL Engine
    VASSAL Engine
    VASSAL is a game engine for creating
    electronic versions of traditional board
    and card games. It provides support for
    game piece rendering and interaction,
    Download VASSAL Engine
  • 3
    OpenPDF - Fork of iText
    OpenPDF - Fork of iText
    OpenPDF is a Java library for creating
    and editing PDF files with a LGPL and
    MPL open source license. OpenPDF is the
    LGPL/MPL open source successor of iText,
    Download OpenPDF - Fork of iText
  • 4
    SAGA - System for Automated
    Geoscientific Analyses - is a Geographic
    Information System (GIS) software with
    immense capabilities for geodata
    processing and ana...
    Download SAGA GIS
  • 5
    Toolbox for Java/JTOpen
    Toolbox for Java/JTOpen
    The IBM Toolbox for Java / JTOpen is a
    library of Java classes supporting the
    client/server and internet programming
    models to a system running OS/400,
    i5/OS, o...
    Download Toolbox for Java/JTOpen
  • 6
    D3.js (or D3 for Data-Driven Documents)
    is a JavaScript library that allows you
    to produce dynamic, interactive data
    visualizations in web browsers. With D3
    Download D3.js
  • More »

Linux commands