1#!/bin/sh
2
3# To view the formatted manual page of this file, type:
4#         POSTFIXSOURCE/mantools/srctoman - postfix-install | nroff -man
5
6#++
7# NAME
8#         postfix-install 1
9# SUMMARY
10#         Postfix installation procedure
11# SYNOPSIS
12#         sh postfix-install [options] [name=value] ...
13# DESCRIPTION
14#         The postfix-install script is to be run from the top-level
15#         Postfix source directory. It implements the following operations:
16# .IP o
17#         Install or upgrade Postfix from source code. This requires
18#         super-user privileges.
19# .IP o
20#         Build a package that can be distributed to other systems, in order
21#         to install or upgrade Postfix elsewhere. This requires no super-user
22#         privileges. To complete the installation after unpacking the
23#         package, execute as super-user the post-install script in the Postfix
24#         configuration directory.
25# .PP
26#         The postfix-install script is controlled by installation parameters.
27#         Specific parameters are described at the end of this document.
28#
29#         By default, postfix-install asks the user for installation
30#         parameter settings. Most settings are stored in the installed
31#         main.cf file. Stored settings are used as site-specific defaults
32#         when the postfix-install script is run later.
33#
34#         The names of Postfix files and directories, as well as their
35#         ownerships and permissions, are stored in the postfix-files file
36#         in the Postfix configuration directory. This information is used
37#         by the post-install script (also in the configuration directory)
38#         for creating missing queue directories when Postfix is started,
39#         and for setting correct ownership and permissions when Postfix
40#         is installed from a pre-built package or from source code.
41#
42#         Arguments
43# .IP -keep-build-mtime
44#         When installing files preserve new file's mtime timestamps.
45#         Otherwise, mtimes will be set to the time that postfix-install
46#         is run.
47# .IP -non-interactive
48#         Do not ask the user for parameter settings. Installation parameters
49#         are specified via one of the non-interactive methods described
50#         below.
51# .IP -package
52#         Build a ready-to-install package. This requires that a
53#         non-default install_root parameter is specified.
54# INSTALLATION PARAMETER INPUT METHODS
55# .ad
56# .fi
57#         Parameter settings can be specified through a variety of
58#         mechanisms.  In order of decreasing precedence these are:
59# .IP "interactive mode"
60#         By default, postfix-install will ask the user for installation
61#         parameter settings. These settings have the highest precedence.
62# .IP "command line"
63#         Parameter settings can be given as name=value arguments on
64#         the postfix-install command line. This mode will replace
65#         the string MAIL_VERSION at the end of a configuration
66#         parameter value with the Postfix release version (Postfix
67#         3.0 and later).
68# .IP "process environment"
69#         Parameter settings can be given as name=value environment
70#         variables. Environment parameters can also be specified on
71#         the make(1) command line as "make install name=value ...".
72#         This mode will replace the string MAIL_VERSION at the end
73#         of a configuration parameter value with the Postfix release
74#         version (Postfix 3.0 and later).
75# .IP "installed configuration files"
76#         If a parameter is not specified via the command line or via the
77#         process environment, postfix-install will attempt to extract its
78#         value from an already installed Postfix main.cf configuration file.
79# .IP "built-in defaults"
80#         These settings have the lowest precedence.
81# INSTALLATION PARAMETER DESCRIPTION
82# .ad
83# .fi
84#         The description of installation parameters and their built-in
85#         default settings is as follows:
86# .IP install_root
87#         Prefix that is prepended to the pathnames of installed files.
88#         Specify this ONLY when creating pre-built packages for distribution to
89#         other systems. The built-in default is "/", the local root directory.
90#         This parameter setting is not recorded in the installed main.cf file.
91# .IP tempdir
92#         Directory for scratch files while installing Postfix.
93#         You must have write permission in this directory.
94#         The built-in default directory name is the current directory.
95#         This parameter setting is not recorded in the installed main.cf file.
96# .IP config_directory
97#         The final destination directory for Postfix configuration files.
98#         The built-in default directory name is /etc/postfix.
99#         This parameter setting is not recorded in the installed main.cf file
100#         and can be changed only by recompiling Postfix.
101# .IP data_directory
102#         The final destination directory for Postfix-writable data files such
103#         as caches. This directory should not be shared with non-Postfix
104#         software. The built-in default directory name is /var/db/postfix.
105#         This parameter setting is recorded in the installed main.cf file.
106# .IP daemon_directory
107#         The final destination directory for Postfix daemon programs. This
108#         directory should not be in the command search path of any users.
109#         The built-in default directory name is /usr/libexec/postfix.
110#         This parameter setting is recorded in the installed main.cf file.
111# .IP command_directory
112#         The final destination directory for Postfix administrative commands.
113#         This directory should be in the command search path of administrative
114#         users. The built-in default directory name is system dependent.
115#         This parameter setting is recorded in the installed main.cf file.
116# .IP html_directory
117#         The final destination directory for the Postfix HTML files.
118#         This parameter setting is recorded in the installed main.cf file.
119# .IP queue_directory
120#         The final destination directory for Postfix queues.
121#         The built-in default directory name is /var/spool/postfix.
122#         This parameter setting is recorded in the installed main.cf file.
123# .IP sendmail_path
124#         The final destination pathname for the Postfix sendmail command.
125#         This is the Sendmail-compatible mail posting interface.
126#         The built-in default pathname is system dependent.
127#         This parameter setting is recorded in the installed main.cf file.
128# .IP newaliases_path
129#         The final destination pathname for the Postfix newaliases command.
130#         This is the Sendmail-compatible command to build alias databases
131#         for the Postfix local delivery agent.
132#         The built-in default pathname is system dependent.
133#         This parameter setting is recorded in the installed main.cf file.
134# .IP mailq_path
135#         The final destination pathname for the Postfix mailq command.
136#         This is the Sendmail-compatible command to list the mail queue.
137#         The built-in default pathname is system dependent.
138#         This parameter setting is recorded in the installed main.cf file.
139# .IP mail_owner
140#         The owner of the Postfix queue. Its numerical user ID and group ID
141#         must not be used by any other accounts on the system.
142#         The built-in default account name is postfix.
143#         This parameter setting is recorded in the installed main.cf file.
144# .IP setgid_group
145#         The group for mail submission and for queue management commands.
146#         Its numerical group ID must not be used by any other accounts on the
147#         system, not even by the mail_owner account.
148#         The built-in default group name is postdrop.
149#         This parameter setting is recorded in the installed main.cf file.
150# .IP manpage_directory
151#         The final destination directory for the Postfix on-line manual pages.
152#         This parameter setting is recorded in the installed main.cf file.
153# .IP sample_directory
154#         The final destination directory for the Postfix sample configuration
155#         files. This parameter is obsolete as of Postfix version 2.1.
156#         This parameter setting is recorded in the installed main.cf file.
157# .IP meta_directory
158#         The final destination directory for non-executable files
159#         that are shared among multiple Postfix instances, such
160#         as postfix-files, dynamicmaps.cf, as well as the multi-instance
161#         template files main.cf.proto and master.cf.proto. This
162#         directory should contain only Postfix-related files.
163# .IP readme_directory
164#         The final destination directory for the Postfix README files.
165#         This parameter setting is recorded in the installed main.cf file.
166# .IP shlib_directory
167#         The final destination directory for Postfix shared-library
168#         files, and the default directory for Postfix database plugin
169#         files with a relative pathname in the file dynamicmaps.cf.
170#         This directory should contain only Postfix-related files.
171#         The shlib_directory parameter built-in default value is
172#         specified at compile time.  If you change this at installation
173#         time, then additional configuration will be required with
174#         ldconfig(1) or equivalent.
175# SEE ALSO
176#         post-install(1) post-installation procedure
177# FILES
178#         $config_directory/main.cf, Postfix installation configuration.
179#         $config_directory/makedefs.out, Postfix 'make makefiles' options.
180#         $meta_directory/postfix-files, installation control file.
181#         $config_directory/install.cf, obsolete configuration file.
182# LICENSE
183# .ad
184# .fi
185#         The Secure Mailer license must be distributed with this software.
186# AUTHOR(S)
187#         Wietse Venema
188#         IBM T.J. Watson Research
189#         P.O. Box 704
190#         Yorktown Heights, NY 10598, USA
191#
192#         Wietse Venema
193#         Google, Inc.
194#         111 8th Avenue
195#         New York, NY 10011, USA
196#
197#         Wietse Venema
198#         porcupine.org
199#         Amawalk, NY 10501, USA
200#--
201
202# Initialize.
203# By now, shells must have functions. Ultrix users must use sh5 or lose.
204
205umask 022
206PATH=/bin:/usr/bin:/usr/sbin:/usr/etc:/sbin:/etc:/usr/contrib/bin:/usr/gnu/bin:/usr/ucb:/usr/bsd
207SHELL=/bin/sh
208IFS="
209"
210BACKUP_IFS="$IFS"
211
212# This script uses outputs from Postfix and non-Postfix commands.
213# Override all LC_* settings and LANG for robustness.
214LC_ALL=C; export LC_ALL
215
216if [ -n "$SHLIB_ENV_VAR" ]; then
217    junk="${SHLIB_ENV_VAL}"
218    eval export "$SHLIB_ENV_VAR=\$junk"
219fi
220
221USAGE="Usage: $0 [name=value] [option]
222    -keep-build-mtime       Preserve build-time file mtime timestamps.
223    -non-interactive        Do not ask for installation parameters.
224    -package                Build a ready-to-install package.
225    name=value              Specify an installation parameter".
226
227# Process command-line options and parameter settings. Work around
228# brain damaged shells. "IFS=value command" should not make the
229# IFS=value setting permanent. But some broken standard allows it.
230
231for arg
232do
233    case $arg in
234*["       "]*) echo "$0: Error: argument contains whitespace: '$arg'"; exit 1;;
235          *=*) IFS= eval $arg; IFS="$BACKUP_IFS";;
236  -non-int*) non_interactive=1;;
237   -package) need_install_root=install_root;;
238-keep-build-mtime)
239             keep_build_mtime=1;;
240            *) echo "$0: Error: $USAGE" 1>&2; exit 1;;
241    esac
242    shift
243done
244
245# Sanity checks.
246
247test -z "$non_interactive" -a ! -t 0 && {
248    echo $0: Error: for non-interactive use, run: \"$0 -non-interactive\" 1>&2
249    exit 1
250}
251
252test -x bin/postconf || {
253    echo $0: Error: no bin/postconf file. Did you forget to run \"make\"? 1>&2
254    exit 1
255}
256
257CONFIG_PARAMS="command_directory daemon_directory data_directory \
258html_directory mail_owner mailq_path manpage_directory newaliases_path \
259queue_directory readme_directory sendmail_path setgid_group shlib_directory \
260meta_directory"
261
262# Expand the string MAIL_VERSION at the end of "make install" etc.
263# name=value command-line arguments (and consequently, in environment
264# settings), for consistency with "make makefiles".
265
266# Note that MAIL_VERSION) does not anchor the match at the end.
267
268for name in $CONFIG_PARAMS sample_directory install_root tempdir
269do
270    eval junk=\$$name
271    case "$junk" in
272    *MAIL_VERSION*)
273          case "$mail_version" in
274          "") mail_version="`bin/postconf -dhx mail_version`" || exit 1
275          esac
276          val=`echo "$junk" | sed 's/MAIL_VERSION$/'"$mail_version/g"` || exit 1
277          case "$val" in
278          *MAIL_VERSION*)
279             echo "MAIL_VERSION not at end of parameter value: $junk" 1>&2; exit 1
280          esac
281          eval ${name}='"$val"'
282    esac
283done
284
285case `uname -s` in
286HP-UX*) FMT=cat;;
287     *) FMT=fmt;;
288esac
289
290# Disclaimer.
291
292test -z "$non_interactive" && cat <<EOF | ${FMT}
293
294    Warning: if you use this script to install Postfix locally,
295    this script will replace existing sendmail or Postfix programs.
296    Make backups if you want to be able to recover.
297
298    Before installing files, this script prompts you for some
299    definitions.  Most definitions will be remembered, so you have
300    to specify them only once. All definitions should have a
301    reasonable default value.
302EOF
303
304# The following shell functions replace files/symlinks while minimizing
305# the time that a file does not exist, and avoid copying over files
306# in order to not disturb running programs. That is certainly desirable
307# when upgrading Postfix on a live machine. It also avoids surprises
308# when building a Postfix package for distribution to other systems.
309
310compare_or_replace() {
311    mode=$1
312    owner=$2
313    group=$3
314    src=$4
315    dst=$5
316    (cmp $src $dst >/dev/null 2>&1 && echo Skipping $dst...) || {
317          echo Updating $dst...
318          rm -f $tempdir/junk || exit 1
319          # Not: "cp -p" which preserves ownership.
320          cp $src $tempdir/junk || exit 1
321          test -z "$keep_build_mtime" || touch -r $src $tempdir/junk || exit 1
322          mv -f $tempdir/junk $dst || exit 1
323          test -z "$owner" || chown $owner $dst || exit 1
324          test -z "$group" || chgrp $group $dst || exit 1
325          chmod $mode $dst || exit 1
326    }
327}
328
329myreadlink() {
330    ls -ld -- "$@" 2>/dev/null | awk '
331          /->/ { print $NF; next }
332          { exit(1) }
333    '
334}
335
336compare_or_symlink() {
337    case $1 in
338    /*) dest=`echo $1 | sed '
339              s;^'$install_root';;
340              s;/\./;/;g
341              s;//*;/;g
342              s;^/;;
343          '`
344          link=`echo $2 | sed '
345              s;^'$install_root';;
346              s;/\./;/;g
347              s;//*;/;g
348              s;^/;;
349              s;/[^/]*$;/;
350              s;[^/]*/;../;g
351              s;$;'$dest';
352          '`
353          ;;
354     *) link=$1
355          ;;
356    esac
357    (test $link = "`myreadlink $2`" >/dev/null 2>&1 && echo Skipping $2...) || {
358          echo Updating $2...
359          # We create the symlink in place instead of using mv because:
360          # 1) some systems cannot move symlinks between file systems;
361          # 2) we cannot use mv to replace a symlink-to-directory;
362          # 3) "ln -n" is not in POSIX, therefore it's not portable.
363          # rm+ln is less atomic but this affects compatibility symlinks only.
364          rm -f $2 && ln -sf $link $2 || exit 1
365    }
366}
367
368compare_or_hardlink() {
369    (cmp $1 $2 >/dev/null 2>&1 && echo Skipping $2...) || {
370          echo Updating $2...
371          rm -f $2 || exit 1
372          ln $1 $2 || exit 1
373    }
374}
375
376check_parent() {
377    for path
378    do
379          dir=`echo $path|sed -e 's/[/][/]*[^/]*$//' -e 's/^$/\//'`
380          test -d $dir || mkdir -p $dir || exit 1
381    done
382}
383
384# How to suppress newlines in echo.
385
386case `echo -n` in
387"") n=-n; c=;;
388 *) n=; c='\c';;
389esac
390
391# Prompts.
392
393install_root_prompt="the prefix for installed file names. Specify
394this ONLY if you are building ready-to-install packages for
395distribution to OTHER machines. See PACKAGE_README for instructions."
396
397tempdir_prompt="a directory for scratch files while installing
398Postfix.  You must have write permission in this directory."
399
400config_directory_prompt="the final destination directory for
401installed Postfix configuration files."
402
403data_directory_prompt="the final destination directory for
404Postfix-writable data files such as caches or random numbers.  This
405directory should not be shared with non-Postfix software."
406
407daemon_directory_prompt="the final destination directory for
408installed Postfix daemon programs.  This directory should not be
409in the command search path of any users."
410
411command_directory_prompt="the final destination directory for
412installed Postfix administrative commands.  This directory should
413be in the command search path of administrative users."
414
415queue_directory_prompt="the final destination directory for Postfix
416queues."
417
418sendmail_path_prompt="the final destination pathname for the
419installed Postfix sendmail command. This is the Sendmail-compatible
420mail posting interface."
421
422newaliases_path_prompt="the final destination pathname for the
423installed Postfix newaliases command.  This is the Sendmail-compatible
424command to build alias databases for the Postfix local delivery
425agent."
426
427mailq_path_prompt="the final destination pathname for the installed
428Postfix mailq command.  This is the Sendmail-compatible mail queue
429listing command."
430
431mail_owner_prompt="the owner of the Postfix queue. Specify an
432account with numerical user ID and group ID values that are not
433used by any other accounts on the system."
434
435setgid_group_prompt="the group for mail submission and for queue
436management commands.  Specify a group name with a numerical group
437ID that is not shared with other accounts, not even with the Postfix
438mail_owner account. You can no longer specify \"no\" here."
439
440manpage_directory_prompt="the final destination directory for the
441Postfix on-line manual pages. You can no longer specify \"no\"
442here."
443
444readme_directory_prompt="the final destination directory for the Postfix
445README files. Specify \"no\" if you do not want to install these files."
446
447html_directory_prompt="the final destination directory for the Postfix
448HTML files. Specify \"no\" if you do not want to install these files."
449
450shlib_directory_prompt="the final destination directory for Postfix
451shared-library files."
452
453meta_directory_prompt="the final destination directory for
454non-executable files that are shared among multiple Postfix instances,
455such as postfix-files, dynamicmaps.cf, as well as the multi-instance
456template files main.cf.proto and master.cf.proto."
457
458# Default settings, just to get started.
459
460: ${install_root=/}
461: ${tempdir=`pwd`}
462: ${config_directory=`bin/postconf -c conf -h -d config_directory`}
463
464# Find out the location of installed configuration files.
465
466test -z "$non_interactive" && for name in install_root tempdir config_directory
467do
468    while :
469    do
470          echo
471          eval echo Please specify \$${name}_prompt | ${FMT}
472          eval echo \$n "$name: [\$$name]\  \$c"
473          read ans
474          case $ans in
475          "") break;;
476           *) case $ans in
477              /*) eval $name=$ans; break;;
478               *) echo; echo $0: Error: $name should be an absolute path name. 1>&2;;
479              esac;;
480          esac
481    done
482done
483
484# In case some systems special-case pathnames beginning with //.
485
486case $install_root in
487/) install_root=
488esac
489
490test -z "$need_install_root" || test -n "$install_root" || {
491    echo $0: Error: invalid package root directory: \"install_root=/\" 1>&2
492    exit 1
493}
494
495CONFIG_DIRECTORY=$install_root$config_directory
496
497# If a parameter is not set via the command line or environment,
498# try to use settings from installed configuration files.
499
500# Extract parameter settings from the obsolete install.cf file, as
501# a transitional aid.
502
503grep setgid_group $CONFIG_DIRECTORY/main.cf >/dev/null 2>&1 || {
504    test -f $CONFIG_DIRECTORY/install.cf && {
505          for name in sendmail_path newaliases_path mailq_path setgid manpages
506          do
507              eval junk=\$$name
508              case "$junk" in
509              "") eval unset $name;;
510              esac
511              eval : \${$name="\`. $CONFIG_DIRECTORY/install.cf; echo \$$name\`"} \
512                    || exit 1
513          done
514          : ${setgid_group=$setgid}
515          : ${manpage_directory=$manpages}
516    }
517}
518
519# Extract parameter settings from the installed main.cf file.
520
521test -f $CONFIG_DIRECTORY/main.cf && {
522    for name in $CONFIG_PARAMS sample_directory
523    do
524          eval junk=\$$name
525          case "$junk" in
526          "") eval unset $name;;
527          esac
528          eval : \${$name=\`bin/postconf -qc $CONFIG_DIRECTORY -hx $name\`} ||
529              exit 1
530    done
531}
532
533# Use built-in defaults as the final source of parameter settings.
534
535for name in $CONFIG_PARAMS sample_directory
536do
537    eval junk=\$$name
538    case "$junk" in
539    "") eval unset $name;;
540    esac
541    eval : \${$name=\`bin/postconf -c conf -d -hx $name\`} || exit 1
542done
543
544# Override settings manually.
545
546test -z "$non_interactive" && for name in $CONFIG_PARAMS
547do
548    while :
549    do
550          echo
551          eval echo Please specify \$${name}_prompt | ${FMT}
552          eval echo \$n "$name: [\$$name]\  \$c"
553          read ans
554          case $ans in
555          "") break;;
556           *) eval $name=$ans; break;;
557          esac
558    done
559done
560
561# Sanity checks
562
563case "$setgid_group" in
564 no) (echo $0: Error: the setgid_group parameter no longer accepts
565     echo \"no\" values. Try again with \"setgid_group=groupname\" on the
566     echo command line or execute \"make install\" and specify setgid_group
567     echo interactively.) | ${FMT} 1>&2
568     exit 1;;
569esac
570
571case "$manpage_directory" in
572 no) (echo $0: Error: the manpage_directory parameter no longer accepts
573     echo \"no\" values.  Try again with \"manpage_directory=/path/name\"
574     echo on the command line or execute \"make install\" and specify
575     echo manpage_directory interactively.) | ${FMT} 1>&2
576     exit 1;;
577esac
578
579for path in "$html_directory" "$readme_directory" "$shlib_directory"
580do
581   case "$path" in
582   /*) ;;
583   no) ;;
584    *) echo $0: Error: \"$path\" should be \"no\" or an absolute path name. 1>&2
585       exit 1;;
586   esac
587done
588
589for path in "$daemon_directory" "$data_directory" "$command_directory" "$queue_directory" \
590    "$sendmail_path" "$newaliases_path" "$mailq_path" "$manpage_directory" \
591    "$meta_directory"
592do
593   case "$path" in
594   /*) ;;
595    *) echo $0: Error: \"$path\" should be an absolute path name. 1>&2; exit 1;;
596   esac
597done
598
599for path in mailq_path newaliases_path sendmail_path
600do
601    eval test -d $install_root\$$path && {
602          echo $0: Error: \"$path\" specifies a directory. 1>&2
603          exit 1
604    }
605done
606
607for path in command_directory config_directory daemon_directory data_directory \
608    manpage_directory queue_directory shlib_directory html_directory \
609    readme_directory meta_directory
610do
611   case "$path" in
612   no) ;;
613    *) eval test -f $install_root\$$path && {
614          echo $0: Error: \"$path\" specifies a regular file. 1>&2
615          exit 1
616   };;
617   esac
618done
619
620# Don't allow space or tab in parameter settings.
621
622for name in $CONFIG_PARAMS sample_directory
623do
624    eval junk=\$$name
625    case "$junk" in
626*"[       ]"*) echo "$0: Error: $name value contains whitespace: '$junk'" 1>&2
627               exit 1;;
628    esac
629done
630
631test -d $tempdir || mkdir -p $tempdir || exit 1
632
633trap "rm -f $tempdir/junk" 0 1 2 3 15
634
635( rm -f $tempdir/junk && touch $tempdir/junk ) || {
636    echo $0: Error: you have no write permission to $tempdir. 1>&2
637    echo Specify an alternative directory for scratch files. 1>&2
638    exit 1
639}
640
641test -z "$install_root" && {
642
643    chown root $tempdir/junk >/dev/null 2>&1 || {
644          echo Error: you have no permission to change file ownership. 1>&2
645          exit 1
646    }
647
648    chown "$mail_owner" $tempdir/junk >/dev/null 2>&1 || {
649          echo $0: Error: \"$mail_owner\" needs an entry in the passwd file. 1>&2
650          echo Remember, \"$mail_owner\" needs a dedicated user and group id. 1>&2
651          exit 1
652    }
653
654    chgrp "$setgid_group" $tempdir/junk >/dev/null 2>&1 || {
655          echo $0: Error: \"$setgid_group\" needs an entry in the group file. 1>&2
656          echo Remember, \"$setgid_group\" needs a dedicated group id. 1>&2
657          exit 1
658    }
659
660}
661
662rm -f $tempdir/junk || exit 1
663
664trap 0 1 2 3 15
665
666# Avoid clumsiness.
667
668DAEMON_DIRECTORY=$install_root$daemon_directory
669COMMAND_DIRECTORY=$install_root$command_directory
670QUEUE_DIRECTORY=$install_root$queue_directory
671SENDMAIL_PATH=$install_root$sendmail_path
672HTML_DIRECTORY=$install_root$html_directory
673MANPAGE_DIRECTORY=$install_root$manpage_directory
674README_DIRECTORY=$install_root$readme_directory
675SHLIB_DIRECTORY=$install_root$shlib_directory
676META_DIRECTORY=$install_root$meta_directory
677
678# Avoid repeated tests for existence of these; default permissions suffice.
679
680test -d $DAEMON_DIRECTORY || mkdir -p $DAEMON_DIRECTORY || exit 1
681test -d $COMMAND_DIRECTORY || mkdir -p $COMMAND_DIRECTORY || exit 1
682test -d $QUEUE_DIRECTORY || mkdir -p $QUEUE_DIRECTORY || exit 1
683test "$shlib_directory" = "no" -o -d $SHLIB_DIRECTORY ||
684          mkdir -p $SHLIB_DIRECTORY || exit 1
685test "$html_directory" = "no" -o -d $HTML_DIRECTORY ||
686          mkdir -p $HTML_DIRECTORY || exit 1
687test "$readme_directory" = "no" -o -d $README_DIRECTORY ||
688          mkdir -p $README_DIRECTORY || exit 1
689test -d $META_DIRECTORY || mkdir -p $META_DIRECTORY || exit 1
690
691# Upgrade or first-time installation?
692
693if [ -f $CONFIG_DIRECTORY/main.cf ]
694then
695    post_install_options="upgrade-source"
696else
697    post_install_options="first-install"
698fi
699
700# Install files, using information from the postfix-files file.
701
702exec < meta/postfix-files || exit 1
703while IFS=: read path type owner group mode flags junk
704do
705    IFS="$BACKUP_IFS"
706
707    # Skip comments.
708
709    case $path in
710    [$]*) ;;
711       *) continue;;
712    esac
713
714    # Skip over files that ought to be removed.
715    # Leave it up to post-install to report them to the user.
716
717    case $flags in
718    *o*) continue
719    esac
720
721    # Skip over files that must be preserved.
722
723    case $flags in
724    *p*) eval test -f $install_root$path && {
725              eval echo "Skipping $install_root$path..."
726              continue
727           };;
728    esac
729
730    # Save source path before it is clobbered.
731
732    case $type in
733    [hl]) eval source=$owner;;
734    esac
735
736    # If installing from source code, apply special permissions or ownership.
737    # If building a package, don't apply special permissions or ownership.
738
739    case $install_root in
740    "") case $owner in
741          [$]*) eval owner=$owner;;
742          root) owner=;;
743          esac
744          case $group in
745          [$]*) eval group=$group;;
746             -) group=;;
747          esac;;
748     *) case $mode in
749          [1-7]755) mode=755;;
750          esac
751          owner=
752          group=;;
753    esac
754
755
756    case $type in
757
758     # Create/update directory.
759
760     d) eval path=$install_root$path
761          test "$path" = "${install_root}no" -o -d $path || {
762              mkdir -p $path || exit 1
763              test -z "$owner" || chown $owner $path || exit 1
764              test -z "$group" || chgrp $group $path || exit 1
765              chmod $mode $path || exit 1
766          }
767          continue;;
768
769     # Create/update regular file.
770
771     f) echo $path | (IFS=/ read prefix file; IFS="$BACKUP_IFS"
772          case $prefix in
773          '$shlib_directory')
774              compare_or_replace $mode "$owner" "$group" lib/$file \
775                        $SHLIB_DIRECTORY/$file || exit 1;;
776          '$meta_directory')
777              compare_or_replace $mode "$owner" "$group" meta/$file \
778                    $META_DIRECTORY/$file || exit 1;;
779          '$daemon_directory')
780              compare_or_replace $mode "$owner" "$group" libexec/$file \
781                    $DAEMON_DIRECTORY/$file || exit 1;;
782          '$command_directory')
783              compare_or_replace $mode "$owner" "$group" bin/$file \
784                    $COMMAND_DIRECTORY/$file || exit 1;;
785          '$config_directory')
786              compare_or_replace $mode "$owner" "$group" conf/$file \
787                    $CONFIG_DIRECTORY/$file || exit 1;;
788          '$sendmail_path')
789              check_parent $SENDMAIL_PATH || exit 1
790              compare_or_replace $mode "$owner" "$group" bin/sendmail \
791                    $SENDMAIL_PATH || exit 1;;
792          '$html_directory')
793              test "$html_directory" = "no" ||
794                    compare_or_replace $mode "$owner" "$group" html/$file \
795                        $HTML_DIRECTORY/$file || exit 1;;
796          '$manpage_directory')
797              check_parent $MANPAGE_DIRECTORY/$file || exit 1
798              compare_or_replace $mode "$owner" "$group" man/$file \
799                    $MANPAGE_DIRECTORY/$file || exit 1;;
800          '$readme_directory')
801              test "$readme_directory" = "no" ||
802                    compare_or_replace $mode "$owner" "$group" README_FILES/$file \
803                        $README_DIRECTORY/$file || exit 1;;
804           *) echo $0: Error: unknown entry $path in meta/postfix-files 1>&2
805              exit 1;;
806          esac) || exit 1
807          continue;;
808
809     # Hard link. Skip files that are not installed.
810
811     h) eval echo $path | (
812              IFS=/ read prefix file; IFS="$BACKUP_IFS"
813              test "$prefix" = "no" || (
814                    eval dest_path=$install_root$path
815                    check_parent $dest_path || exit 1
816                    eval source_path=$install_root$source
817                    compare_or_hardlink $source_path $dest_path || exit 1
818              )
819          ) || exit 1
820          continue;;
821
822     # Symbolic link. Skip files that are not installed.
823
824     l) eval echo $path | (
825              IFS=/ read prefix file; IFS="$BACKUP_IFS"
826              test "$prefix" = "no" || (
827                    eval dest_path=$install_root$path
828                    check_parent $dest_path || exit 1
829                    eval source_path=$install_root$source
830                    compare_or_symlink $source_path $dest_path || exit 1
831              )
832          ) || exit 1
833          continue;;
834
835     *) echo $0: Error: unknown type $type for $path in meta/postfix-files 1>&2
836          exit 1;;
837    esac
838
839done
840# More (solaris9) shell brain damage!
841IFS="$BACKUP_IFS"
842
843# Save the installation parameters to main.cf even when they haven't
844# changed from their current default. Defaults can change between
845# Postfix releases, and software should not suddenly be installed in
846# the wrong place when Postfix is being upgraded.
847
848case "$mail_version" in
849"") mail_version="`bin/postconf -dhx mail_version`" || exit 1
850esac
851
852# Undo MAIL_VERSION expansion at the end of a parameter value. If
853# someone really wants the expanded mail version in main.cf, then
854# we're sorry.
855
856for name in $CONFIG_PARAMS sample_directory
857do
858    eval junk=\$$name
859    case "$junk" in
860    *"$mail_version"*)
861          case "$pattern" in
862          "") pattern=`echo "$mail_version" | sed 's/\./\\\\./g'` || exit 1
863          esac
864          val=`echo "$junk" | sed "s/$pattern"'$/${mail_version}/g'` || exit 1
865          eval ${name}='"$val"'
866    esac
867done
868
869bin/postconf -qc $CONFIG_DIRECTORY -e \
870    "daemon_directory = $daemon_directory" \
871    "data_directory = $data_directory" \
872    "command_directory = $command_directory" \
873    "queue_directory = $queue_directory" \
874    "mail_owner = $mail_owner" \
875    "setgid_group = $setgid_group" \
876    "sendmail_path = $sendmail_path" \
877    "mailq_path = $mailq_path" \
878    "newaliases_path = $newaliases_path" \
879    "html_directory = $html_directory" \
880    "manpage_directory = $manpage_directory" \
881    "sample_directory = $sample_directory" \
882    "readme_directory = $readme_directory" \
883    "shlib_directory = $shlib_directory" \
884    "meta_directory = $meta_directory" \
885|| exit 1
886
887# If Postfix is being installed locally from source code, do the
888# post-install processing now.
889
890# The unexpansion above may have side effects on exported variables.
891# It does not matter because bin/postfix below will override them.
892
893test -n "$install_root" || {
894    bin/postfix post-install $post_install_options || exit 1
895}
896