1937a2000SPeter Wemm#!/bin/sh 2937a2000SPeter Wemm# install - install a program, script, or datafile 3937a2000SPeter Wemm 4*70b56f4bSCy Schubertscriptversion=2020-11-14.01; # UTC 5937a2000SPeter Wemm 6937a2000SPeter Wemm# This originates from X11R5 (mit/util/scripts/install.sh), which was 7937a2000SPeter Wemm# later released in X11R6 (xc/config/util/install.sh) with the 8937a2000SPeter Wemm# following copyright and license. 9937a2000SPeter Wemm# 10937a2000SPeter Wemm# Copyright (C) 1994 X Consortium 11937a2000SPeter Wemm# 12937a2000SPeter Wemm# Permission is hereby granted, free of charge, to any person obtaining a copy 13937a2000SPeter Wemm# of this software and associated documentation files (the "Software"), to 14937a2000SPeter Wemm# deal in the Software without restriction, including without limitation the 15937a2000SPeter Wemm# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or 16937a2000SPeter Wemm# sell copies of the Software, and to permit persons to whom the Software is 17937a2000SPeter Wemm# furnished to do so, subject to the following conditions: 18937a2000SPeter Wemm# 19937a2000SPeter Wemm# The above copyright notice and this permission notice shall be included in 20937a2000SPeter Wemm# all copies or substantial portions of the Software. 21937a2000SPeter Wemm# 22937a2000SPeter Wemm# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 23937a2000SPeter Wemm# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 24937a2000SPeter Wemm# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 25937a2000SPeter Wemm# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN 26937a2000SPeter Wemm# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC- 27937a2000SPeter Wemm# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 28937a2000SPeter Wemm# 29937a2000SPeter Wemm# Except as contained in this notice, the name of the X Consortium shall not 30937a2000SPeter Wemm# be used in advertising or otherwise to promote the sale, use or other deal- 31937a2000SPeter Wemm# ings in this Software without prior written authorization from the X Consor- 32937a2000SPeter Wemm# tium. 33937a2000SPeter Wemm# 34937a2000SPeter Wemm# 35937a2000SPeter Wemm# FSF changes to this file are in the public domain. 36937a2000SPeter Wemm# 37937a2000SPeter Wemm# Calling this script install-sh is preferred over install.sh, to prevent 38d915215eSBaptiste Daroussin# 'make' implicit rules from creating a file called install from it 39937a2000SPeter Wemm# when there is no Makefile. 40937a2000SPeter Wemm# 41937a2000SPeter Wemm# This script is compatible with the BSD install script, but was written 428bc5c7c0SPeter Wemm# from scratch. 438bc5c7c0SPeter Wemm 44d915215eSBaptiste Daroussintab=' ' 458bc5c7c0SPeter Wemmnl=' 468bc5c7c0SPeter Wemm' 47d915215eSBaptiste DaroussinIFS=" $tab$nl" 48937a2000SPeter Wemm 49d915215eSBaptiste Daroussin# Set DOITPROG to "echo" to test this script. 50937a2000SPeter Wemm 518bc5c7c0SPeter Wemmdoit=${DOITPROG-} 52d915215eSBaptiste Daroussindoit_exec=${doit:-exec} 53937a2000SPeter Wemm 548bc5c7c0SPeter Wemm# Put in absolute file names if you don't have them in your path; 558bc5c7c0SPeter Wemm# or use environment vars. 56937a2000SPeter Wemm 578bc5c7c0SPeter Wemmchgrpprog=${CHGRPPROG-chgrp} 588bc5c7c0SPeter Wemmchmodprog=${CHMODPROG-chmod} 598bc5c7c0SPeter Wemmchownprog=${CHOWNPROG-chown} 608bc5c7c0SPeter Wemmcmpprog=${CMPPROG-cmp} 618bc5c7c0SPeter Wemmcpprog=${CPPROG-cp} 628bc5c7c0SPeter Wemmmkdirprog=${MKDIRPROG-mkdir} 638bc5c7c0SPeter Wemmmvprog=${MVPROG-mv} 648bc5c7c0SPeter Wemmrmprog=${RMPROG-rm} 658bc5c7c0SPeter Wemmstripprog=${STRIPPROG-strip} 66937a2000SPeter Wemm 678bc5c7c0SPeter Wemmposix_mkdir= 688bc5c7c0SPeter Wemm 698bc5c7c0SPeter Wemm# Desired mode of installed file. 708bc5c7c0SPeter Wemmmode=0755 718bc5c7c0SPeter Wemm 72*70b56f4bSCy Schubert# Create dirs (including intermediate dirs) using mode 755. 73*70b56f4bSCy Schubert# This is like GNU 'install' as of coreutils 8.32 (2020). 74*70b56f4bSCy Schubertmkdir_umask=22 75*70b56f4bSCy Schubert 76*70b56f4bSCy Schubertbackupsuffix= 77937a2000SPeter Wemmchgrpcmd= 788bc5c7c0SPeter Wemmchmodcmd=$chmodprog 798bc5c7c0SPeter Wemmchowncmd= 808bc5c7c0SPeter Wemmmvcmd=$mvprog 81937a2000SPeter Wemmrmcmd="$rmprog -f" 828bc5c7c0SPeter Wemmstripcmd= 838bc5c7c0SPeter Wemm 84937a2000SPeter Wemmsrc= 85937a2000SPeter Wemmdst= 86937a2000SPeter Wemmdir_arg= 878bc5c7c0SPeter Wemmdst_arg= 888bc5c7c0SPeter Wemm 898bc5c7c0SPeter Wemmcopy_on_change=false 90d915215eSBaptiste Daroussinis_target_a_directory=possibly 91937a2000SPeter Wemm 928bc5c7c0SPeter Wemmusage="\ 938bc5c7c0SPeter WemmUsage: $0 [OPTION]... [-T] SRCFILE DSTFILE 94937a2000SPeter Wemm or: $0 [OPTION]... SRCFILES... DIRECTORY 95937a2000SPeter Wemm or: $0 [OPTION]... -t DIRECTORY SRCFILES... 96937a2000SPeter Wemm or: $0 [OPTION]... -d DIRECTORIES... 97937a2000SPeter Wemm 98937a2000SPeter WemmIn the 1st form, copy SRCFILE to DSTFILE. 99937a2000SPeter WemmIn the 2nd and 3rd, copy all SRCFILES to DIRECTORY. 100937a2000SPeter WemmIn the 4th, create DIRECTORIES. 101937a2000SPeter Wemm 102937a2000SPeter WemmOptions: 1038bc5c7c0SPeter Wemm --help display this help and exit. 1048bc5c7c0SPeter Wemm --version display version info and exit. 1058bc5c7c0SPeter Wemm 106937a2000SPeter Wemm -c (ignored) 107*70b56f4bSCy Schubert -C install only if different (preserve data modification time) 108937a2000SPeter Wemm -d create directories instead of installing files. 109937a2000SPeter Wemm -g GROUP $chgrpprog installed files to GROUP. 110937a2000SPeter Wemm -m MODE $chmodprog installed files to MODE. 111937a2000SPeter Wemm -o USER $chownprog installed files to USER. 112*70b56f4bSCy Schubert -p pass -p to $cpprog. 113937a2000SPeter Wemm -s $stripprog installed files. 114*70b56f4bSCy Schubert -S SUFFIX attempt to back up existing files, with suffix SUFFIX. 115937a2000SPeter Wemm -t DIRECTORY install into DIRECTORY. 116937a2000SPeter Wemm -T report an error if DSTFILE is a directory. 117937a2000SPeter Wemm 118937a2000SPeter WemmEnvironment variables override the default commands: 1198bc5c7c0SPeter Wemm CHGRPPROG CHMODPROG CHOWNPROG CMPPROG CPPROG MKDIRPROG MVPROG 1208bc5c7c0SPeter Wemm RMPROG STRIPPROG 121*70b56f4bSCy Schubert 122*70b56f4bSCy SchubertBy default, rm is invoked with -f; when overridden with RMPROG, 123*70b56f4bSCy Schubertit's up to you to specify -f if you want it. 124*70b56f4bSCy Schubert 125*70b56f4bSCy SchubertIf -S is not specified, no backups are attempted. 126*70b56f4bSCy Schubert 127*70b56f4bSCy SchubertEmail bug reports to bug-automake@gnu.org. 128*70b56f4bSCy SchubertAutomake home page: https://www.gnu.org/software/automake/ 129937a2000SPeter Wemm" 130937a2000SPeter Wemm 1318bc5c7c0SPeter Wemmwhile test $# -ne 0; do 132937a2000SPeter Wemm case $1 in 1338bc5c7c0SPeter Wemm -c) ;; 134937a2000SPeter Wemm 1358bc5c7c0SPeter Wemm -C) copy_on_change=true;; 1368bc5c7c0SPeter Wemm 1378bc5c7c0SPeter Wemm -d) dir_arg=true;; 138937a2000SPeter Wemm 139937a2000SPeter Wemm -g) chgrpcmd="$chgrpprog $2" 1408bc5c7c0SPeter Wemm shift;; 141937a2000SPeter Wemm 142937a2000SPeter Wemm --help) echo "$usage"; exit $?;; 143937a2000SPeter Wemm 1448bc5c7c0SPeter Wemm -m) mode=$2 1458bc5c7c0SPeter Wemm case $mode in 146d915215eSBaptiste Daroussin *' '* | *"$tab"* | *"$nl"* | *'*'* | *'?'* | *'['*) 1478bc5c7c0SPeter Wemm echo "$0: invalid mode: $mode" >&2 1488bc5c7c0SPeter Wemm exit 1;; 1498bc5c7c0SPeter Wemm esac 1508bc5c7c0SPeter Wemm shift;; 151937a2000SPeter Wemm 152937a2000SPeter Wemm -o) chowncmd="$chownprog $2" 1538bc5c7c0SPeter Wemm shift;; 154937a2000SPeter Wemm 155*70b56f4bSCy Schubert -p) cpprog="$cpprog -p";; 156*70b56f4bSCy Schubert 1578bc5c7c0SPeter Wemm -s) stripcmd=$stripprog;; 158937a2000SPeter Wemm 159*70b56f4bSCy Schubert -S) backupsuffix="$2" 160*70b56f4bSCy Schubert shift;; 161*70b56f4bSCy Schubert 162d915215eSBaptiste Daroussin -t) 163d915215eSBaptiste Daroussin is_target_a_directory=always 164d915215eSBaptiste Daroussin dst_arg=$2 165d915215eSBaptiste Daroussin # Protect names problematic for 'test' and other utilities. 1668bc5c7c0SPeter Wemm case $dst_arg in 1678bc5c7c0SPeter Wemm -* | [=\(\)!]) dst_arg=./$dst_arg;; 1688bc5c7c0SPeter Wemm esac 1698bc5c7c0SPeter Wemm shift;; 170937a2000SPeter Wemm 171d915215eSBaptiste Daroussin -T) is_target_a_directory=never;; 172937a2000SPeter Wemm 173937a2000SPeter Wemm --version) echo "$0 $scriptversion"; exit $?;; 174937a2000SPeter Wemm 1758bc5c7c0SPeter Wemm --) shift 1768bc5c7c0SPeter Wemm break;; 1778bc5c7c0SPeter Wemm 1788bc5c7c0SPeter Wemm -*) echo "$0: invalid option: $1" >&2 1798bc5c7c0SPeter Wemm exit 1;; 1808bc5c7c0SPeter Wemm 1818bc5c7c0SPeter Wemm *) break;; 1828bc5c7c0SPeter Wemm esac 1838bc5c7c0SPeter Wemm shift 1848bc5c7c0SPeter Wemmdone 1858bc5c7c0SPeter Wemm 186d915215eSBaptiste Daroussin# We allow the use of options -d and -T together, by making -d 187d915215eSBaptiste Daroussin# take the precedence; this is for compatibility with GNU install. 188d915215eSBaptiste Daroussin 189d915215eSBaptiste Daroussinif test -n "$dir_arg"; then 190d915215eSBaptiste Daroussin if test -n "$dst_arg"; then 191d915215eSBaptiste Daroussin echo "$0: target directory not allowed when installing a directory." >&2 192d915215eSBaptiste Daroussin exit 1 193d915215eSBaptiste Daroussin fi 194d915215eSBaptiste Daroussinfi 195d915215eSBaptiste Daroussin 1968bc5c7c0SPeter Wemmif test $# -ne 0 && test -z "$dir_arg$dst_arg"; then 1978bc5c7c0SPeter Wemm # When -d is used, all remaining arguments are directories to create. 198937a2000SPeter Wemm # When -t is used, the destination is already specified. 199937a2000SPeter Wemm # Otherwise, the last argument is the destination. Remove it from $@. 200937a2000SPeter Wemm for arg 201937a2000SPeter Wemm do 2028bc5c7c0SPeter Wemm if test -n "$dst_arg"; then 203937a2000SPeter Wemm # $@ is not empty: it contains at least $arg. 2048bc5c7c0SPeter Wemm set fnord "$@" "$dst_arg" 205937a2000SPeter Wemm shift # fnord 206937a2000SPeter Wemm fi 207937a2000SPeter Wemm shift # arg 2088bc5c7c0SPeter Wemm dst_arg=$arg 209d915215eSBaptiste Daroussin # Protect names problematic for 'test' and other utilities. 2108bc5c7c0SPeter Wemm case $dst_arg in 2118bc5c7c0SPeter Wemm -* | [=\(\)!]) dst_arg=./$dst_arg;; 212937a2000SPeter Wemm esac 213937a2000SPeter Wemm done 2148bc5c7c0SPeter Wemmfi 215937a2000SPeter Wemm 2168bc5c7c0SPeter Wemmif test $# -eq 0; then 217937a2000SPeter Wemm if test -z "$dir_arg"; then 218937a2000SPeter Wemm echo "$0: no input file specified." >&2 219937a2000SPeter Wemm exit 1 220937a2000SPeter Wemm fi 221d915215eSBaptiste Daroussin # It's OK to call 'install-sh -d' without argument. 222937a2000SPeter Wemm # This can happen when creating conditional directories. 223937a2000SPeter Wemm exit 0 224937a2000SPeter Wemmfi 225937a2000SPeter Wemm 2268bc5c7c0SPeter Wemmif test -z "$dir_arg"; then 227d915215eSBaptiste Daroussin if test $# -gt 1 || test "$is_target_a_directory" = always; then 228d915215eSBaptiste Daroussin if test ! -d "$dst_arg"; then 229d915215eSBaptiste Daroussin echo "$0: $dst_arg: Is not a directory." >&2 230d915215eSBaptiste Daroussin exit 1 231d915215eSBaptiste Daroussin fi 232d915215eSBaptiste Daroussin fi 233d915215eSBaptiste Daroussinfi 234d915215eSBaptiste Daroussin 235d915215eSBaptiste Daroussinif test -z "$dir_arg"; then 2368bc5c7c0SPeter Wemm do_exit='(exit $ret); exit $ret' 2378bc5c7c0SPeter Wemm trap "ret=129; $do_exit" 1 2388bc5c7c0SPeter Wemm trap "ret=130; $do_exit" 2 2398bc5c7c0SPeter Wemm trap "ret=141; $do_exit" 13 2408bc5c7c0SPeter Wemm trap "ret=143; $do_exit" 15 2418bc5c7c0SPeter Wemm 2428bc5c7c0SPeter Wemm # Set umask so as not to create temps with too-generous modes. 2438bc5c7c0SPeter Wemm # However, 'strip' requires both read and write access to temps. 2448bc5c7c0SPeter Wemm case $mode in 2458bc5c7c0SPeter Wemm # Optimize common cases. 2468bc5c7c0SPeter Wemm *644) cp_umask=133;; 2478bc5c7c0SPeter Wemm *755) cp_umask=22;; 2488bc5c7c0SPeter Wemm 2498bc5c7c0SPeter Wemm *[0-7]) 2508bc5c7c0SPeter Wemm if test -z "$stripcmd"; then 2518bc5c7c0SPeter Wemm u_plus_rw= 2528bc5c7c0SPeter Wemm else 2538bc5c7c0SPeter Wemm u_plus_rw='% 200' 2548bc5c7c0SPeter Wemm fi 2558bc5c7c0SPeter Wemm cp_umask=`expr '(' 777 - $mode % 1000 ')' $u_plus_rw`;; 2568bc5c7c0SPeter Wemm *) 2578bc5c7c0SPeter Wemm if test -z "$stripcmd"; then 2588bc5c7c0SPeter Wemm u_plus_rw= 2598bc5c7c0SPeter Wemm else 2608bc5c7c0SPeter Wemm u_plus_rw=,u+rw 2618bc5c7c0SPeter Wemm fi 2628bc5c7c0SPeter Wemm cp_umask=$mode$u_plus_rw;; 2638bc5c7c0SPeter Wemm esac 2648bc5c7c0SPeter Wemmfi 2658bc5c7c0SPeter Wemm 266937a2000SPeter Wemmfor src 267937a2000SPeter Wemmdo 268d915215eSBaptiste Daroussin # Protect names problematic for 'test' and other utilities. 269937a2000SPeter Wemm case $src in 2708bc5c7c0SPeter Wemm -* | [=\(\)!]) src=./$src;; 271937a2000SPeter Wemm esac 272937a2000SPeter Wemm 273937a2000SPeter Wemm if test -n "$dir_arg"; then 274937a2000SPeter Wemm dst=$src 2758bc5c7c0SPeter Wemm dstdir=$dst 2768bc5c7c0SPeter Wemm test -d "$dstdir" 2778bc5c7c0SPeter Wemm dstdir_status=$? 278*70b56f4bSCy Schubert # Don't chown directories that already exist. 279*70b56f4bSCy Schubert if test $dstdir_status = 0; then 280*70b56f4bSCy Schubert chowncmd="" 281*70b56f4bSCy Schubert fi 2828bc5c7c0SPeter Wemm else 283937a2000SPeter Wemm 284937a2000SPeter Wemm # Waiting for this to be detected by the "$cpprog $src $dsttmp" command 285937a2000SPeter Wemm # might cause directories to be created, which would be especially bad 286937a2000SPeter Wemm # if $src (and thus $dsttmp) contains '*'. 287937a2000SPeter Wemm if test ! -f "$src" && test ! -d "$src"; then 288937a2000SPeter Wemm echo "$0: $src does not exist." >&2 289937a2000SPeter Wemm exit 1 290937a2000SPeter Wemm fi 291937a2000SPeter Wemm 2928bc5c7c0SPeter Wemm if test -z "$dst_arg"; then 293937a2000SPeter Wemm echo "$0: no destination specified." >&2 294937a2000SPeter Wemm exit 1 295937a2000SPeter Wemm fi 2968bc5c7c0SPeter Wemm dst=$dst_arg 297937a2000SPeter Wemm 298*70b56f4bSCy Schubert # If destination is a directory, append the input filename. 299937a2000SPeter Wemm if test -d "$dst"; then 300d915215eSBaptiste Daroussin if test "$is_target_a_directory" = never; then 3018bc5c7c0SPeter Wemm echo "$0: $dst_arg: Is a directory" >&2 302937a2000SPeter Wemm exit 1 303937a2000SPeter Wemm fi 3048bc5c7c0SPeter Wemm dstdir=$dst 305*70b56f4bSCy Schubert dstbase=`basename "$src"` 306*70b56f4bSCy Schubert case $dst in 307*70b56f4bSCy Schubert */) dst=$dst$dstbase;; 308*70b56f4bSCy Schubert *) dst=$dst/$dstbase;; 309*70b56f4bSCy Schubert esac 3108bc5c7c0SPeter Wemm dstdir_status=0 3118bc5c7c0SPeter Wemm else 312d915215eSBaptiste Daroussin dstdir=`dirname "$dst"` 3138bc5c7c0SPeter Wemm test -d "$dstdir" 3148bc5c7c0SPeter Wemm dstdir_status=$? 315937a2000SPeter Wemm fi 316937a2000SPeter Wemm fi 317937a2000SPeter Wemm 318*70b56f4bSCy Schubert case $dstdir in 319*70b56f4bSCy Schubert */) dstdirslash=$dstdir;; 320*70b56f4bSCy Schubert *) dstdirslash=$dstdir/;; 321*70b56f4bSCy Schubert esac 322*70b56f4bSCy Schubert 3238bc5c7c0SPeter Wemm obsolete_mkdir_used=false 324937a2000SPeter Wemm 3258bc5c7c0SPeter Wemm if test $dstdir_status != 0; then 3268bc5c7c0SPeter Wemm case $posix_mkdir in 3278bc5c7c0SPeter Wemm '') 3288bc5c7c0SPeter Wemm # With -d, create the new directory with the user-specified mode. 3298bc5c7c0SPeter Wemm # Otherwise, rely on $mkdir_umask. 3308bc5c7c0SPeter Wemm if test -n "$dir_arg"; then 3318bc5c7c0SPeter Wemm mkdir_mode=-m$mode 3328bc5c7c0SPeter Wemm else 3338bc5c7c0SPeter Wemm mkdir_mode= 3348bc5c7c0SPeter Wemm fi 3358bc5c7c0SPeter Wemm 3368bc5c7c0SPeter Wemm posix_mkdir=false 337*70b56f4bSCy Schubert # The $RANDOM variable is not portable (e.g., dash). Use it 338*70b56f4bSCy Schubert # here however when possible just to lower collision chance. 3398bc5c7c0SPeter Wemm tmpdir=${TMPDIR-/tmp}/ins$RANDOM-$$ 3408bc5c7c0SPeter Wemm 341*70b56f4bSCy Schubert trap ' 342*70b56f4bSCy Schubert ret=$? 343*70b56f4bSCy Schubert rmdir "$tmpdir/a/b" "$tmpdir/a" "$tmpdir" 2>/dev/null 344*70b56f4bSCy Schubert exit $ret 345*70b56f4bSCy Schubert ' 0 346*70b56f4bSCy Schubert 347*70b56f4bSCy Schubert # Because "mkdir -p" follows existing symlinks and we likely work 348*70b56f4bSCy Schubert # directly in world-writeable /tmp, make sure that the '$tmpdir' 349*70b56f4bSCy Schubert # directory is successfully created first before we actually test 350*70b56f4bSCy Schubert # 'mkdir -p'. 3518bc5c7c0SPeter Wemm if (umask $mkdir_umask && 352bca4681bSCy Schubert $mkdirprog $mkdir_mode "$tmpdir" && 353bca4681bSCy Schubert exec $mkdirprog $mkdir_mode -p -- "$tmpdir/a/b") >/dev/null 2>&1 3548bc5c7c0SPeter Wemm then 3558bc5c7c0SPeter Wemm if test -z "$dir_arg" || { 3568bc5c7c0SPeter Wemm # Check for POSIX incompatibilities with -m. 3578bc5c7c0SPeter Wemm # HP-UX 11.23 and IRIX 6.5 mkdir -m -p sets group- or 358d915215eSBaptiste Daroussin # other-writable bit of parent directory when it shouldn't. 3598bc5c7c0SPeter Wemm # FreeBSD 6.1 mkdir -m -p sets mode of existing directory. 360bca4681bSCy Schubert test_tmpdir="$tmpdir/a" 361bca4681bSCy Schubert ls_ld_tmpdir=`ls -ld "$test_tmpdir"` 3628bc5c7c0SPeter Wemm case $ls_ld_tmpdir in 3638bc5c7c0SPeter Wemm d????-?r-*) different_mode=700;; 3648bc5c7c0SPeter Wemm d????-?--*) different_mode=755;; 3658bc5c7c0SPeter Wemm *) false;; 3668bc5c7c0SPeter Wemm esac && 367bca4681bSCy Schubert $mkdirprog -m$different_mode -p -- "$test_tmpdir" && { 368bca4681bSCy Schubert ls_ld_tmpdir_1=`ls -ld "$test_tmpdir"` 3698bc5c7c0SPeter Wemm test "$ls_ld_tmpdir" = "$ls_ld_tmpdir_1" 3708bc5c7c0SPeter Wemm } 3718bc5c7c0SPeter Wemm } 3728bc5c7c0SPeter Wemm then posix_mkdir=: 3738bc5c7c0SPeter Wemm fi 374bca4681bSCy Schubert rmdir "$tmpdir/a/b" "$tmpdir/a" "$tmpdir" 3758bc5c7c0SPeter Wemm else 3768bc5c7c0SPeter Wemm # Remove any dirs left behind by ancient mkdir implementations. 377bca4681bSCy Schubert rmdir ./$mkdir_mode ./-p ./-- "$tmpdir" 2>/dev/null 3788bc5c7c0SPeter Wemm fi 3798bc5c7c0SPeter Wemm trap '' 0;; 3808bc5c7c0SPeter Wemm esac 3818bc5c7c0SPeter Wemm 3828bc5c7c0SPeter Wemm if 3838bc5c7c0SPeter Wemm $posix_mkdir && ( 3848bc5c7c0SPeter Wemm umask $mkdir_umask && 3858bc5c7c0SPeter Wemm $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir" 3868bc5c7c0SPeter Wemm ) 3878bc5c7c0SPeter Wemm then : 3888bc5c7c0SPeter Wemm else 3898bc5c7c0SPeter Wemm 390*70b56f4bSCy Schubert # mkdir does not conform to POSIX, 3918bc5c7c0SPeter Wemm # or it failed possibly due to a race condition. Create the 3928bc5c7c0SPeter Wemm # directory the slow way, step by step, checking for races as we go. 3938bc5c7c0SPeter Wemm 3948bc5c7c0SPeter Wemm case $dstdir in 3958bc5c7c0SPeter Wemm /*) prefix='/';; 3968bc5c7c0SPeter Wemm [-=\(\)!]*) prefix='./';; 3978bc5c7c0SPeter Wemm *) prefix='';; 3988bc5c7c0SPeter Wemm esac 3998bc5c7c0SPeter Wemm 400937a2000SPeter Wemm oIFS=$IFS 4018bc5c7c0SPeter Wemm IFS=/ 402d915215eSBaptiste Daroussin set -f 4038bc5c7c0SPeter Wemm set fnord $dstdir 404937a2000SPeter Wemm shift 405d915215eSBaptiste Daroussin set +f 406937a2000SPeter Wemm IFS=$oIFS 407937a2000SPeter Wemm 4088bc5c7c0SPeter Wemm prefixes= 409937a2000SPeter Wemm 4108bc5c7c0SPeter Wemm for d 4118bc5c7c0SPeter Wemm do 4128bc5c7c0SPeter Wemm test X"$d" = X && continue 4138bc5c7c0SPeter Wemm 4148bc5c7c0SPeter Wemm prefix=$prefix$d 4158bc5c7c0SPeter Wemm if test -d "$prefix"; then 4168bc5c7c0SPeter Wemm prefixes= 4178bc5c7c0SPeter Wemm else 4188bc5c7c0SPeter Wemm if $posix_mkdir; then 419*70b56f4bSCy Schubert (umask $mkdir_umask && 4208bc5c7c0SPeter Wemm $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir") && break 4218bc5c7c0SPeter Wemm # Don't fail if two instances are running concurrently. 4228bc5c7c0SPeter Wemm test -d "$prefix" || exit 1 4238bc5c7c0SPeter Wemm else 4248bc5c7c0SPeter Wemm case $prefix in 4258bc5c7c0SPeter Wemm *\'*) qprefix=`echo "$prefix" | sed "s/'/'\\\\\\\\''/g"`;; 4268bc5c7c0SPeter Wemm *) qprefix=$prefix;; 4278bc5c7c0SPeter Wemm esac 4288bc5c7c0SPeter Wemm prefixes="$prefixes '$qprefix'" 429937a2000SPeter Wemm fi 4308bc5c7c0SPeter Wemm fi 4318bc5c7c0SPeter Wemm prefix=$prefix/ 432937a2000SPeter Wemm done 4338bc5c7c0SPeter Wemm 4348bc5c7c0SPeter Wemm if test -n "$prefixes"; then 4358bc5c7c0SPeter Wemm # Don't fail if two instances are running concurrently. 4368bc5c7c0SPeter Wemm (umask $mkdir_umask && 4378bc5c7c0SPeter Wemm eval "\$doit_exec \$mkdirprog $prefixes") || 4388bc5c7c0SPeter Wemm test -d "$dstdir" || exit 1 4398bc5c7c0SPeter Wemm obsolete_mkdir_used=true 4408bc5c7c0SPeter Wemm fi 4418bc5c7c0SPeter Wemm fi 442937a2000SPeter Wemm fi 443937a2000SPeter Wemm 444937a2000SPeter Wemm if test -n "$dir_arg"; then 4458bc5c7c0SPeter Wemm { test -z "$chowncmd" || $doit $chowncmd "$dst"; } && 4468bc5c7c0SPeter Wemm { test -z "$chgrpcmd" || $doit $chgrpcmd "$dst"; } && 4478bc5c7c0SPeter Wemm { test "$obsolete_mkdir_used$chowncmd$chgrpcmd" = false || 4488bc5c7c0SPeter Wemm test -z "$chmodcmd" || $doit $chmodcmd $mode "$dst"; } || exit 1 449937a2000SPeter Wemm else 450937a2000SPeter Wemm 451937a2000SPeter Wemm # Make a couple of temp file names in the proper directory. 452*70b56f4bSCy Schubert dsttmp=${dstdirslash}_inst.$$_ 453*70b56f4bSCy Schubert rmtmp=${dstdirslash}_rm.$$_ 454937a2000SPeter Wemm 455937a2000SPeter Wemm # Trap to clean up those temp files at exit. 456937a2000SPeter Wemm trap 'ret=$?; rm -f "$dsttmp" "$rmtmp" && exit $ret' 0 457937a2000SPeter Wemm 458937a2000SPeter Wemm # Copy the file name to the temp name. 459*70b56f4bSCy Schubert (umask $cp_umask && 460*70b56f4bSCy Schubert { test -z "$stripcmd" || { 461*70b56f4bSCy Schubert # Create $dsttmp read-write so that cp doesn't create it read-only, 462*70b56f4bSCy Schubert # which would cause strip to fail. 463*70b56f4bSCy Schubert if test -z "$doit"; then 464*70b56f4bSCy Schubert : >"$dsttmp" # No need to fork-exec 'touch'. 465*70b56f4bSCy Schubert else 466*70b56f4bSCy Schubert $doit touch "$dsttmp" 467*70b56f4bSCy Schubert fi 468*70b56f4bSCy Schubert } 469*70b56f4bSCy Schubert } && 470*70b56f4bSCy Schubert $doit_exec $cpprog "$src" "$dsttmp") && 471937a2000SPeter Wemm 472937a2000SPeter Wemm # and set any options; do chmod last to preserve setuid bits. 473937a2000SPeter Wemm # 474937a2000SPeter Wemm # If any of these fail, we abort the whole thing. If we want to 475937a2000SPeter Wemm # ignore errors from any of these, just make sure not to ignore 476937a2000SPeter Wemm # errors from the above "$doit $cpprog $src $dsttmp" command. 477937a2000SPeter Wemm # 4788bc5c7c0SPeter Wemm { test -z "$chowncmd" || $doit $chowncmd "$dsttmp"; } && 4798bc5c7c0SPeter Wemm { test -z "$chgrpcmd" || $doit $chgrpcmd "$dsttmp"; } && 4808bc5c7c0SPeter Wemm { test -z "$stripcmd" || $doit $stripcmd "$dsttmp"; } && 4818bc5c7c0SPeter Wemm { test -z "$chmodcmd" || $doit $chmodcmd $mode "$dsttmp"; } && 482937a2000SPeter Wemm 4838bc5c7c0SPeter Wemm # If -C, don't bother to copy if it wouldn't change the file. 4848bc5c7c0SPeter Wemm if $copy_on_change && 4858bc5c7c0SPeter Wemm old=`LC_ALL=C ls -dlL "$dst" 2>/dev/null` && 4868bc5c7c0SPeter Wemm new=`LC_ALL=C ls -dlL "$dsttmp" 2>/dev/null` && 487d915215eSBaptiste Daroussin set -f && 4888bc5c7c0SPeter Wemm set X $old && old=:$2:$4:$5:$6 && 4898bc5c7c0SPeter Wemm set X $new && new=:$2:$4:$5:$6 && 490d915215eSBaptiste Daroussin set +f && 4918bc5c7c0SPeter Wemm test "$old" = "$new" && 4928bc5c7c0SPeter Wemm $cmpprog "$dst" "$dsttmp" >/dev/null 2>&1 4938bc5c7c0SPeter Wemm then 4948bc5c7c0SPeter Wemm rm -f "$dsttmp" 4958bc5c7c0SPeter Wemm else 496*70b56f4bSCy Schubert # If $backupsuffix is set, and the file being installed 497*70b56f4bSCy Schubert # already exists, attempt a backup. Don't worry if it fails, 498*70b56f4bSCy Schubert # e.g., if mv doesn't support -f. 499*70b56f4bSCy Schubert if test -n "$backupsuffix" && test -f "$dst"; then 500*70b56f4bSCy Schubert $doit $mvcmd -f "$dst" "$dst$backupsuffix" 2>/dev/null 501*70b56f4bSCy Schubert fi 502*70b56f4bSCy Schubert 5038bc5c7c0SPeter Wemm # Rename the file to the real destination. 5048bc5c7c0SPeter Wemm $doit $mvcmd -f "$dsttmp" "$dst" 2>/dev/null || 5058bc5c7c0SPeter Wemm 506937a2000SPeter Wemm # The rename failed, perhaps because mv can't rename something else 507937a2000SPeter Wemm # to itself, or perhaps because mv is so ancient that it does not 508937a2000SPeter Wemm # support -f. 5098bc5c7c0SPeter Wemm { 510937a2000SPeter Wemm # Now remove or move aside any old file at destination location. 511937a2000SPeter Wemm # We try this two ways since rm can't unlink itself on some 512937a2000SPeter Wemm # systems and the destination file might be busy for other 513937a2000SPeter Wemm # reasons. In this case, the final cleanup might fail but the new 514937a2000SPeter Wemm # file should still install successfully. 515937a2000SPeter Wemm { 5168bc5c7c0SPeter Wemm test ! -f "$dst" || 517*70b56f4bSCy Schubert $doit $rmcmd "$dst" 2>/dev/null || 5188bc5c7c0SPeter Wemm { $doit $mvcmd -f "$dst" "$rmtmp" 2>/dev/null && 519*70b56f4bSCy Schubert { $doit $rmcmd "$rmtmp" 2>/dev/null; :; } 5208bc5c7c0SPeter Wemm } || 5218bc5c7c0SPeter Wemm { echo "$0: cannot unlink or rename $dst" >&2 522937a2000SPeter Wemm (exit 1); exit 1 523937a2000SPeter Wemm } 524937a2000SPeter Wemm } && 525937a2000SPeter Wemm 526937a2000SPeter Wemm # Now rename the file to the real destination. 5278bc5c7c0SPeter Wemm $doit $mvcmd "$dsttmp" "$dst" 528937a2000SPeter Wemm } 5298bc5c7c0SPeter Wemm fi || exit 1 530937a2000SPeter Wemm 5318bc5c7c0SPeter Wemm trap '' 0 5328bc5c7c0SPeter Wemm fi 5338bc5c7c0SPeter Wemmdone 534937a2000SPeter Wemm 535937a2000SPeter Wemm# Local variables: 536*70b56f4bSCy Schubert# eval: (add-hook 'before-save-hook 'time-stamp) 537937a2000SPeter Wemm# time-stamp-start: "scriptversion=" 538937a2000SPeter Wemm# time-stamp-format: "%:y-%02m-%02d.%02H" 539*70b56f4bSCy Schubert# time-stamp-time-zone: "UTC0" 5408bc5c7c0SPeter Wemm# time-stamp-end: "; # UTC" 541937a2000SPeter Wemm# End: 542