4.2 Configure with m4
The
process of building a sendmail configuration
file begins by creating a file of m4 statements.
Traditionally, the suffix for such files is .mc.
The cf/cf directory contains examples of many
.mc files. Of special interest are those that
begin with generic, for these can serve as
boilerplates in developing your own .mc files:
generic-bsd4.4.mc generic-mpeix.mc generic-sunos4.1.mc
generic-hpux10.mc generic-nextstep3.3.mc generic-ultrix4.mc
generic-hpux9.mc generic-osf1.mc
generic-linux.mc generic-solaris.mc
All .mc files require specific minimal statements.
For a SunOS 4.1.4 site on the Internet, for example, the following
are minimal:
OSTYPE(sunos4.1)dnl see Section 4.2.2.1
MAILER(local)dnl see Section 4.2.2.2
MAILER(smtp)dnl see Section 4.2.2.2
To build a configuration file from these statements, you would place
them into a file—say,
localsun.mc—then run the following
command:
% ./Build localsun.cf
Using M4=/usr/5bin/m4
rm -f localsun.cf
/usr/5bin/m4 ../m4/cf.m4 localsun.mc > localsun.cf || ( rm -f localsun.cf && exit 1 )
chmod 444 localsun.cf
Here, you run the Build script found in
the cf/cf directory. You pass it the name of
your mc file with the
".mc" suffix changed to a
".cf" suffix. The
Build script uses m4 to
expand your mc file into a full-fledged
configuration file.
Another way to build a configuration file is by running
m4 by hand:
% m4 ../m4/cf.m4 localsun.mc > sendmail.cf
Here, the ../m4/cf.m4 tells
m4 where to look for its default configuration
file information.
If you are using an old version of
m4, the following error message will be printed:
You need a newer version of M4, at least as new as
System V or GNU
m4: file not found: NoSuchFile
Just as the message says, you need a newer version of
m4. (The third line is just a result of forcing
m4 to fail and can be safely ignored.) Thus, we
would need to rerun our second localsun.mc
example (earlier) as:
% /usr/5bin/m4 ../m4/cf.m4 localsun.mc > sendmail.cf
System V version of m4
Another cause of failure could be that the
../m4/cf.m4 file was not where you thought it was.
Various versions of m4 print this error in
different ways:
/usr/5bin/m4:-:1 can't open file SysV m4
m4: ../m4/cf.m4: No such file or directory GNU m4
m4: file not found: ../m4/cf.m4 BSD m4
One possible reason for this error might be that you are developing
your .mc file somewhere other than in the
cf/cf directory. The solution is to use a full pathname to
cf.m4 or to replace that expression on the
command line with a shell variable.
After you have successfully produced a "first
draft" of your configuration file, you can edit
localsun.mc and add features as you need them.
Many possibilities are described in the rest of this chapter.
4.2.1 The _CF_DIR_ m4 Macro
It can be
advantageous to maintain all the files that make up your local
m4 configuration separately from the
sendmail distribution. This prevents new
releases of sendmail from clobbering your source
files. It also allows you to maintain configuration information more
conveniently (perhaps under rcs(1) control) and
to use programs such as make(1) to simplify
configuring and installation.
Most modern versions of m4 allow you to define
m4 macros on the command line, and one such
m4 macro is recognized internally by the
m4 technique:
_CF_DIR_
This command-line m4 macro tells
m4 where the m4/cf.m4 file
described earlier is located. It needs to have its value set to be
the cf directory under the
sendmail source distribution, and it needs to
end in a slash character. For example, GNU m4
version 1.2 allows this:
% setenv CFDIR /usr/local/src/mail/sendmail/cf/
% /usr/local/gnu/bin/m4 -D_CF_DIR_=${CFDIR} ${CFDIR}m4/cf.m4 localsun.mc \
> sendmail.cf
Notice that we store the value for _CF_DIR_ in an
environment variable. Note that GNU m4 can
figure out the _CF_DIR_ path itself from the path
of the cf.m4 file. We include
_CF_DIR_ here merely as an example. If your
version of m4 lacks this ability, you should
consider upgrading.
With the _CF_DIR_ m4 macro,
we can further simplify configuration and installation by using
make(1). To illustrate, consider the following
few lines from a Makefile on a SunOS system:
M4=/usr/local/gnu/bin/m4
CFDIR=/usr/local/src/mail/sendmail/cf/
localsun: localsun.mc
$(M4) -D_CF_DIR_=$(CFDIR) $(CFDIR)/m4/cf.m4 localsun.mc > sendmail.cf
With this Makefile the two complex command lines
shown earlier are reduced to a single, simple command line:
% make
4.2.2 The Minimal mc File
Every
mc file requires minimal information. Table 4-1 shows which m4 items are
required and lists two that are recommended. We show them in the
order that they should be declared (OSTYPE first and MAILER last),
then describe the mandatory and recommended information.
Table 4-1. Required and recommended m4 items
OSTYPE( )
|
Section 4.2.2.1
|
Required
|
Support for your operating system
|
DOMAIN( )
|
Section 4.2.2.3
|
Recommended
|
Common domain-wide information
|
FEATURE( )
|
Section 4.2.2.4
|
Recommended
|
Solutions to special needs
|
MAILER( )
|
Section 4.2.2.2
|
Required
|
Necessary delivery agents
|
Note that what is minimally required for a workstation differs from
what is minimally required for a central mail server. We suggest that
you use these recommendations as a jumping-off point and then
investigate all the m4 macros and features that
are available.
4.2.2.1 OSTYPE( ) m4 macro
Support for various operating systems is
supplied with the OSTYPE m4 command. Every
.mc file must declare the
operating system with this command, and this command must be the
first in your mc file. The available support is supplied by
files in the _CF_DIR_/ostype directory. A
listing of those files looks something like this:
a-ux.m4 bsdi2.0.m4 hpux9.m4 openbsd.m4 solaris2.ml.m4
aix3.m4 darwin.m4 irix4.m4 osf1.m4 solaris2.pre5.m4
aix4.m4 dgux.m4 irix5.m4 powerux.m4 solaris8.m4
aix5.m4 domainos.m4 irix6.m4 ptx2.m4 sunos3.5.m4
altos.m4 dynix3.2.m4 isc4.1.m4 qnx.m4 sunos4.1.m4
amdahl-uts.m4 freebsd4.m4 linux.m4 riscos4.5.m4 svr4.m4
bsd4.3.m4 freebsd5.m4 maxion.m4 sco-uw-2.1.m4 ultrix4.m4
bsd4.4.m4 gnu.m4 mklinux.m4 sco3.2.m4 unixware7.m4
bsdi.m4 hpux10.m4 mpeix.m4 sinix.m4 unknown.m4
bsdi1.0.m4 hpux11.m4 nextstep.m4 solaris2.m4 uxpds.m4
To include support, select the file that best describes your
operating system, delete the .m4 suffix from its
name, and include the resulting name in an OSTYPE declaration:
OSTYPE(`ultrix4')
Here, support for the DEC Ultrix operating system is defined. Note
that some of these are not entirely accurate. For example,
ultrix4.m4 includes support for Ultrix versions
4.2 and 4.3, and sunos4.1.m4 includes support for
SunOS versions 4.1.2, 4.1.3., and 4.1.4.
If you pick a name for which no file exists, or if you misspell the
name of the file, an error similar to the following will print:
m4: Can't open ../ostype/ultrux4.1.m4: No such file or directory
If you omit the OSTYPE declaration entirely, you will get the
following error:
*** ERROR: No system type defined (use OSTYPE macro)
4.2.2.2 MAILER( ) m4 macro
Delivery agents are not automatically
declared. Instead, you must specify which ones you want to support
and which ones you want to ignore. Support is included by using the
MAILER definition:
MAILER(`local')
This causes support for both the local and
prog delivery agents to be included. This is the
minimal declaration (even if you don't intend to
perform local or program delivery).
The MAILER definition must always be last in your
mc configuration file. If you include
MAILER definitions for procmail(1),
maildrop(1), or uucp, those
definitions must always follow the definition for
smtp. Any modification of a MAILER definition (as,
for example, with LOCAL_MAILER_MAX) must precede that MAILER
definition:
define(`LOCAL_MAILER_MAX', `1000000') here
MAILER(`local')
define(`LOCAL_MAILER_MAX', `1000000') not here
A minimal mc file for an average machine on the
Internet would contain two MAILER definitions:
MAILER(`local')
MAILER(`smtp')
The first you have already seen. The second includes support for
sending email to other hosts on the Internet. If this minimal
mc is all you think you'll
need, you can continue on to the rest of this chapter. If, on the
other hand, you expect to support any variations on mail receipt and
delivery beyond the basics, you should leap ahead to Chapter 20, study that chapter, then return here. (See
Table 20-1 in Section 20.3 for a
list of all the available delivery agents.)
All delivery agent equates, such as F= and
M=, can be modified with the
.m4 configuration technique. Table 20-18 (Section 20.5) lists all the
equates and shows where to find further information about each of
them. By investigating those sections, you can discover how to tune
particular equates with the m4 technique. For
example, the following mc lines define the
program used for local delivery to be
mail.local:
FEATURE(`local_lmtp')
define(`LOCAL_MAILER_PATH', `/usr/local/bin/mail.local')
MAILER(local)
Note that all modifications to equates must precede the corresponding
MAILER( ) definition.
4.2.2.3 DOMAIN( ) m4 macro
For
large sites it can be advantageous to gather into a single file all
configuration decisions that are common to the entire domain. The
directory to hold domain information files is called
domain. The configuration information in those
files is accessed by using the DOMAIN( ) m4
technique. For example:
DOMAIN(`uofa.edu')
This line in any of your mc files causes the
file domain/uofa.edu.m4 to be included at that
point. Examples that come with the distribution illustrate subdomains
under Berkeley.EDU. One boilerplate file, named
generic.m4, can be used as a starting point for
your own domainwide file. For example, if all hosts at your site
masquerade behind one email name, you might want to put MASQUERADE_AS
(Section 4.4.2) in your domain file. Domain files also
form a natural location for the definition of site-specific relays
(Section 4.5).
If the domain that is specified does not exist or is misspelled, an
error similar to the following will be printed:
m4: Can't open ../domain/generik.m4: No such file or directory
The use of DOMAIN( ) is not mandatory but is recommended. Note that
problems can arise because the items inside your domain file will
determine where the DOMAIN( ) declaration must go in the
mc file. If, for example, the domain file
contains MAILER( ) definitions, DOMAIN( ) should appear near the end
of the mc file with the MAILER( ) definitions.
If the domain file contains rules and rule sets, the DOMAIN( ) must
be last in the mc file, but if the domain file
contains OSTYPE( ), DOMAIN( ) must be first in the
mc file. So, consider well what you place in
your domain file. Avoid defining anything in your domain file that
restricts where the DOMAIN( ) definition must go in your
mc file.
In the event that your domain file contains many position-dependent
commands, such as rule sets and an OSTYPE( ) command, you might need
to split that file into pieces. You can split it something like this:
DOMAIN(`our.domain.sun')
DOMAIN(`our.domain.rules')
Here, the first line causes the file
our.domain.sun.m4 to be read. That file contains
the OSTYPE( ) declaration for all your Sun workstations. This DOMAIN(
) entry would appear at the top of your mc file.
The second line causes the file
our.domain.rules.m4 to be read. That file might
contain antispam rule sets. This second DOMAIN( ) entry would appear
near the end of your mc file, perhaps under
LOCAL_RULESETS.
4.2.2.4 FEATURE( ) m4 macro
V8
sendmail offers a number of features that you
might find very useful. To use a feature, include an
m4 command such as one of the following in your
mc file:
FEATURE(keyword)
FEATURE(keyword, argument)
FEATURE(keyword, argument, argument, ... etc. )
These declarations cause a file of the name
feature/keyword.m4 to
be read at that place in your mc file. The
available keyword files are summarized in Table 4-7 of Section 4.8, and each is
explained in the section at the end of this chapter. Note that some
keywords require additional arguments.
4.2.3 The Order of mc Lines
As you have seen, some mc lines must precede
others. This is necessary partly because m4(1)
is a one-pass program, and partly because the order of items in the
final sendmail.cf file is also critical. The
recommended order is:
VERSIONID( ) see Section 4.2.3.1
OSTYPE( ) see Section 4.2.2.1
DOMAIN( ) see Section 4.2.2.3
option definitions see Section 24.4
FEATURE( ) see Section 4.8
macro definitions see Section 21.7
MAILER( ) see Section 4.2.2.2
ruleset definitions see Section 19.1.7
If in doubt about where some particular item should go, look in the
many example files in cf/cf. Some of them
(especially the file knecht.mc) will also give
you good ideas about how you can improve your own
mc file.
4.2.3.1 VERSIONID m4 macro
The VERSIONID m4
macro is used to insert an identifier into each
mc and m4 file that becomes
a part of your final .cf file. Each file that is
supplied with sendmail already has such an
identifier. You should include a similar identifier in each of your
mc files:
VERSIONID(`$Id$')
Here, the VERSIONID m4 macro is used to insert
an RCS-style revision number. The $Id: ch04,v 1.53
2002/12/12 21:54:32 judyh Exp judyh $ becomes an actual
version number when the file is checked in with
ci(1). Arbitrary text can appear between the
single quotes. You can use RCS, SCCS, or any other kind of revision
identification system. The text cannot contain a newline because the
text appears in the .cf file as a comment:
##### $Id: ch04.xml,v 1.7 2003/03/28 19:05:54 becki Exp $ #####
Use of VERSIONID and revision control in general is recommended.
4.2.3.2 HACK( ) m4 macro
Some things
just can't be called features. To make this clear,
they go in the hack directory and are referenced
using the HACK m4 macro. They tend to be
site-dependent:
HACK(`cssubdomain')
This illustrates use of the Berkeley-dependent
cssubdomain hack (that makes
sendmail accept local names in either
Berkeley.EDU or
CS.Berkeley.EDU).
Another way to think of a hack is as a transient feature. Create and
use HACK as a temporary solution to a temporary problem. If a
solution becomes permanent, move it to the FEATURE directory and
reference it there.
|