install-sh revision 82e12b1b
121c2f794Smrg#!/bin/sh 221c2f794Smrg# install - install a program, script, or datafile 321c2f794Smrg 482e12b1bSmrgscriptversion=2011-01-19.21; # UTC 521c2f794Smrg 621c2f794Smrg# This originates from X11R5 (mit/util/scripts/install.sh), which was 721c2f794Smrg# later released in X11R6 (xc/config/util/install.sh) with the 821c2f794Smrg# following copyright and license. 921c2f794Smrg# 1021c2f794Smrg# Copyright (C) 1994 X Consortium 1121c2f794Smrg# 1221c2f794Smrg# Permission is hereby granted, free of charge, to any person obtaining a copy 1321c2f794Smrg# of this software and associated documentation files (the "Software"), to 1421c2f794Smrg# deal in the Software without restriction, including without limitation the 1521c2f794Smrg# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or 1621c2f794Smrg# sell copies of the Software, and to permit persons to whom the Software is 1721c2f794Smrg# furnished to do so, subject to the following conditions: 1821c2f794Smrg# 1921c2f794Smrg# The above copyright notice and this permission notice shall be included in 2021c2f794Smrg# all copies or substantial portions of the Software. 2121c2f794Smrg# 2221c2f794Smrg# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 2321c2f794Smrg# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 2421c2f794Smrg# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 2521c2f794Smrg# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN 2621c2f794Smrg# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC- 2721c2f794Smrg# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 2821c2f794Smrg# 2921c2f794Smrg# Except as contained in this notice, the name of the X Consortium shall not 3021c2f794Smrg# be used in advertising or otherwise to promote the sale, use or other deal- 3121c2f794Smrg# ings in this Software without prior written authorization from the X Consor- 3221c2f794Smrg# tium. 3321c2f794Smrg# 3421c2f794Smrg# 3521c2f794Smrg# FSF changes to this file are in the public domain. 3621c2f794Smrg# 3721c2f794Smrg# Calling this script install-sh is preferred over install.sh, to prevent 3821c2f794Smrg# `make' implicit rules from creating a file called install from it 3921c2f794Smrg# when there is no Makefile. 4021c2f794Smrg# 4121c2f794Smrg# This script is compatible with the BSD install script, but was written 4221c2f794Smrg# from scratch. 4321c2f794Smrg 4421c2f794Smrgnl=' 4521c2f794Smrg' 4621c2f794SmrgIFS=" "" $nl" 4721c2f794Smrg 4821c2f794Smrg# set DOITPROG to echo to test this script 4921c2f794Smrg 5021c2f794Smrg# Don't use :- since 4.3BSD and earlier shells don't like it. 5112391620Smrgdoit=${DOITPROG-} 5221c2f794Smrgif test -z "$doit"; then 5321c2f794Smrg doit_exec=exec 5421c2f794Smrgelse 5521c2f794Smrg doit_exec=$doit 5621c2f794Smrgfi 5721c2f794Smrg 5821c2f794Smrg# Put in absolute file names if you don't have them in your path; 5921c2f794Smrg# or use environment vars. 6021c2f794Smrg 6112391620Smrgchgrpprog=${CHGRPPROG-chgrp} 6212391620Smrgchmodprog=${CHMODPROG-chmod} 6312391620Smrgchownprog=${CHOWNPROG-chown} 6412391620Smrgcmpprog=${CMPPROG-cmp} 6512391620Smrgcpprog=${CPPROG-cp} 6612391620Smrgmkdirprog=${MKDIRPROG-mkdir} 6712391620Smrgmvprog=${MVPROG-mv} 6812391620Smrgrmprog=${RMPROG-rm} 6912391620Smrgstripprog=${STRIPPROG-strip} 7012391620Smrg 7112391620Smrgposix_glob='?' 7212391620Smrginitialize_posix_glob=' 7312391620Smrg test "$posix_glob" != "?" || { 7412391620Smrg if (set -f) 2>/dev/null; then 7512391620Smrg posix_glob= 7612391620Smrg else 7712391620Smrg posix_glob=: 7812391620Smrg fi 7912391620Smrg } 8012391620Smrg' 8121c2f794Smrg 8221c2f794Smrgposix_mkdir= 8321c2f794Smrg 8421c2f794Smrg# Desired mode of installed file. 8521c2f794Smrgmode=0755 8621c2f794Smrg 8712391620Smrgchgrpcmd= 8821c2f794Smrgchmodcmd=$chmodprog 8921c2f794Smrgchowncmd= 9012391620Smrgmvcmd=$mvprog 9121c2f794Smrgrmcmd="$rmprog -f" 9212391620Smrgstripcmd= 9312391620Smrg 9421c2f794Smrgsrc= 9521c2f794Smrgdst= 9621c2f794Smrgdir_arg= 9712391620Smrgdst_arg= 9812391620Smrg 9912391620Smrgcopy_on_change=false 10021c2f794Smrgno_target_directory= 10121c2f794Smrg 10212391620Smrgusage="\ 10312391620SmrgUsage: $0 [OPTION]... [-T] SRCFILE DSTFILE 10421c2f794Smrg or: $0 [OPTION]... SRCFILES... DIRECTORY 10521c2f794Smrg or: $0 [OPTION]... -t DIRECTORY SRCFILES... 10621c2f794Smrg or: $0 [OPTION]... -d DIRECTORIES... 10721c2f794Smrg 10821c2f794SmrgIn the 1st form, copy SRCFILE to DSTFILE. 10921c2f794SmrgIn the 2nd and 3rd, copy all SRCFILES to DIRECTORY. 11021c2f794SmrgIn the 4th, create DIRECTORIES. 11121c2f794Smrg 11221c2f794SmrgOptions: 11312391620Smrg --help display this help and exit. 11412391620Smrg --version display version info and exit. 11512391620Smrg 11612391620Smrg -c (ignored) 11712391620Smrg -C install only if different (preserve the last data modification time) 11812391620Smrg -d create directories instead of installing files. 11912391620Smrg -g GROUP $chgrpprog installed files to GROUP. 12012391620Smrg -m MODE $chmodprog installed files to MODE. 12112391620Smrg -o USER $chownprog installed files to USER. 12212391620Smrg -s $stripprog installed files. 12312391620Smrg -t DIRECTORY install into DIRECTORY. 12412391620Smrg -T report an error if DSTFILE is a directory. 12521c2f794Smrg 12621c2f794SmrgEnvironment variables override the default commands: 12712391620Smrg CHGRPPROG CHMODPROG CHOWNPROG CMPPROG CPPROG MKDIRPROG MVPROG 12812391620Smrg RMPROG STRIPPROG 12921c2f794Smrg" 13021c2f794Smrg 13121c2f794Smrgwhile test $# -ne 0; do 13221c2f794Smrg case $1 in 13312391620Smrg -c) ;; 13412391620Smrg 13512391620Smrg -C) copy_on_change=true;; 13621c2f794Smrg 13712391620Smrg -d) dir_arg=true;; 13821c2f794Smrg 13921c2f794Smrg -g) chgrpcmd="$chgrpprog $2" 14012391620Smrg shift;; 14121c2f794Smrg 14221c2f794Smrg --help) echo "$usage"; exit $?;; 14321c2f794Smrg 14421c2f794Smrg -m) mode=$2 14521c2f794Smrg case $mode in 14621c2f794Smrg *' '* | *' '* | *' 14721c2f794Smrg'* | *'*'* | *'?'* | *'['*) 14821c2f794Smrg echo "$0: invalid mode: $mode" >&2 14921c2f794Smrg exit 1;; 15021c2f794Smrg esac 15112391620Smrg shift;; 15221c2f794Smrg 15321c2f794Smrg -o) chowncmd="$chownprog $2" 15412391620Smrg shift;; 15521c2f794Smrg 15612391620Smrg -s) stripcmd=$stripprog;; 15721c2f794Smrg 15812391620Smrg -t) dst_arg=$2 15982e12b1bSmrg # Protect names problematic for `test' and other utilities. 16082e12b1bSmrg case $dst_arg in 16182e12b1bSmrg -* | [=\(\)!]) dst_arg=./$dst_arg;; 16282e12b1bSmrg esac 16312391620Smrg shift;; 16421c2f794Smrg 16512391620Smrg -T) no_target_directory=true;; 16621c2f794Smrg 16721c2f794Smrg --version) echo "$0 $scriptversion"; exit $?;; 16821c2f794Smrg 16921c2f794Smrg --) shift 17021c2f794Smrg break;; 17121c2f794Smrg 17221c2f794Smrg -*) echo "$0: invalid option: $1" >&2 17321c2f794Smrg exit 1;; 17421c2f794Smrg 17521c2f794Smrg *) break;; 17621c2f794Smrg esac 17712391620Smrg shift 17821c2f794Smrgdone 17921c2f794Smrg 18012391620Smrgif test $# -ne 0 && test -z "$dir_arg$dst_arg"; then 18121c2f794Smrg # When -d is used, all remaining arguments are directories to create. 18221c2f794Smrg # When -t is used, the destination is already specified. 18321c2f794Smrg # Otherwise, the last argument is the destination. Remove it from $@. 18421c2f794Smrg for arg 18521c2f794Smrg do 18612391620Smrg if test -n "$dst_arg"; then 18721c2f794Smrg # $@ is not empty: it contains at least $arg. 18812391620Smrg set fnord "$@" "$dst_arg" 18921c2f794Smrg shift # fnord 19021c2f794Smrg fi 19121c2f794Smrg shift # arg 19212391620Smrg dst_arg=$arg 19382e12b1bSmrg # Protect names problematic for `test' and other utilities. 19482e12b1bSmrg case $dst_arg in 19582e12b1bSmrg -* | [=\(\)!]) dst_arg=./$dst_arg;; 19682e12b1bSmrg esac 19721c2f794Smrg done 19821c2f794Smrgfi 19921c2f794Smrg 20021c2f794Smrgif test $# -eq 0; then 20121c2f794Smrg if test -z "$dir_arg"; then 20221c2f794Smrg echo "$0: no input file specified." >&2 20321c2f794Smrg exit 1 20421c2f794Smrg fi 20521c2f794Smrg # It's OK to call `install-sh -d' without argument. 20621c2f794Smrg # This can happen when creating conditional directories. 20721c2f794Smrg exit 0 20821c2f794Smrgfi 20921c2f794Smrg 21021c2f794Smrgif test -z "$dir_arg"; then 21182e12b1bSmrg do_exit='(exit $ret); exit $ret' 21282e12b1bSmrg trap "ret=129; $do_exit" 1 21382e12b1bSmrg trap "ret=130; $do_exit" 2 21482e12b1bSmrg trap "ret=141; $do_exit" 13 21582e12b1bSmrg trap "ret=143; $do_exit" 15 21621c2f794Smrg 21721c2f794Smrg # Set umask so as not to create temps with too-generous modes. 21821c2f794Smrg # However, 'strip' requires both read and write access to temps. 21921c2f794Smrg case $mode in 22021c2f794Smrg # Optimize common cases. 22121c2f794Smrg *644) cp_umask=133;; 22221c2f794Smrg *755) cp_umask=22;; 22321c2f794Smrg 22421c2f794Smrg *[0-7]) 22521c2f794Smrg if test -z "$stripcmd"; then 22621c2f794Smrg u_plus_rw= 22721c2f794Smrg else 22821c2f794Smrg u_plus_rw='% 200' 22921c2f794Smrg fi 23021c2f794Smrg cp_umask=`expr '(' 777 - $mode % 1000 ')' $u_plus_rw`;; 23121c2f794Smrg *) 23221c2f794Smrg if test -z "$stripcmd"; then 23321c2f794Smrg u_plus_rw= 23421c2f794Smrg else 23521c2f794Smrg u_plus_rw=,u+rw 23621c2f794Smrg fi 23721c2f794Smrg cp_umask=$mode$u_plus_rw;; 23821c2f794Smrg esac 23921c2f794Smrgfi 24021c2f794Smrg 24121c2f794Smrgfor src 24221c2f794Smrgdo 24382e12b1bSmrg # Protect names problematic for `test' and other utilities. 24421c2f794Smrg case $src in 24582e12b1bSmrg -* | [=\(\)!]) src=./$src;; 24621c2f794Smrg esac 24721c2f794Smrg 24821c2f794Smrg if test -n "$dir_arg"; then 24921c2f794Smrg dst=$src 25021c2f794Smrg dstdir=$dst 25121c2f794Smrg test -d "$dstdir" 25221c2f794Smrg dstdir_status=$? 25321c2f794Smrg else 25421c2f794Smrg 25521c2f794Smrg # Waiting for this to be detected by the "$cpprog $src $dsttmp" command 25621c2f794Smrg # might cause directories to be created, which would be especially bad 25721c2f794Smrg # if $src (and thus $dsttmp) contains '*'. 25821c2f794Smrg if test ! -f "$src" && test ! -d "$src"; then 25921c2f794Smrg echo "$0: $src does not exist." >&2 26021c2f794Smrg exit 1 26121c2f794Smrg fi 26221c2f794Smrg 26312391620Smrg if test -z "$dst_arg"; then 26421c2f794Smrg echo "$0: no destination specified." >&2 26521c2f794Smrg exit 1 26621c2f794Smrg fi 26712391620Smrg dst=$dst_arg 26821c2f794Smrg 26921c2f794Smrg # If destination is a directory, append the input filename; won't work 27021c2f794Smrg # if double slashes aren't ignored. 27121c2f794Smrg if test -d "$dst"; then 27221c2f794Smrg if test -n "$no_target_directory"; then 27312391620Smrg echo "$0: $dst_arg: Is a directory" >&2 27421c2f794Smrg exit 1 27521c2f794Smrg fi 27621c2f794Smrg dstdir=$dst 27721c2f794Smrg dst=$dstdir/`basename "$src"` 27821c2f794Smrg dstdir_status=0 27921c2f794Smrg else 28021c2f794Smrg # Prefer dirname, but fall back on a substitute if dirname fails. 28121c2f794Smrg dstdir=` 28221c2f794Smrg (dirname "$dst") 2>/dev/null || 28321c2f794Smrg expr X"$dst" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ 28421c2f794Smrg X"$dst" : 'X\(//\)[^/]' \| \ 28521c2f794Smrg X"$dst" : 'X\(//\)$' \| \ 28621c2f794Smrg X"$dst" : 'X\(/\)' \| . 2>/dev/null || 28721c2f794Smrg echo X"$dst" | 28821c2f794Smrg sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ 28921c2f794Smrg s//\1/ 29021c2f794Smrg q 29121c2f794Smrg } 29221c2f794Smrg /^X\(\/\/\)[^/].*/{ 29321c2f794Smrg s//\1/ 29421c2f794Smrg q 29521c2f794Smrg } 29621c2f794Smrg /^X\(\/\/\)$/{ 29721c2f794Smrg s//\1/ 29821c2f794Smrg q 29921c2f794Smrg } 30021c2f794Smrg /^X\(\/\).*/{ 30121c2f794Smrg s//\1/ 30221c2f794Smrg q 30321c2f794Smrg } 30421c2f794Smrg s/.*/./; q' 30521c2f794Smrg ` 30621c2f794Smrg 30721c2f794Smrg test -d "$dstdir" 30821c2f794Smrg dstdir_status=$? 30921c2f794Smrg fi 31021c2f794Smrg fi 31121c2f794Smrg 31221c2f794Smrg obsolete_mkdir_used=false 31321c2f794Smrg 31421c2f794Smrg if test $dstdir_status != 0; then 31521c2f794Smrg case $posix_mkdir in 31621c2f794Smrg '') 31721c2f794Smrg # Create intermediate dirs using mode 755 as modified by the umask. 31821c2f794Smrg # This is like FreeBSD 'install' as of 1997-10-28. 31921c2f794Smrg umask=`umask` 32021c2f794Smrg case $stripcmd.$umask in 32121c2f794Smrg # Optimize common cases. 32221c2f794Smrg *[2367][2367]) mkdir_umask=$umask;; 32321c2f794Smrg .*0[02][02] | .[02][02] | .[02]) mkdir_umask=22;; 32421c2f794Smrg 32521c2f794Smrg *[0-7]) 32621c2f794Smrg mkdir_umask=`expr $umask + 22 \ 32721c2f794Smrg - $umask % 100 % 40 + $umask % 20 \ 32821c2f794Smrg - $umask % 10 % 4 + $umask % 2 32921c2f794Smrg `;; 33021c2f794Smrg *) mkdir_umask=$umask,go-w;; 33121c2f794Smrg esac 33221c2f794Smrg 33321c2f794Smrg # With -d, create the new directory with the user-specified mode. 33421c2f794Smrg # Otherwise, rely on $mkdir_umask. 33521c2f794Smrg if test -n "$dir_arg"; then 33621c2f794Smrg mkdir_mode=-m$mode 33721c2f794Smrg else 33821c2f794Smrg mkdir_mode= 33921c2f794Smrg fi 34021c2f794Smrg 34121c2f794Smrg posix_mkdir=false 34221c2f794Smrg case $umask in 34321c2f794Smrg *[123567][0-7][0-7]) 34421c2f794Smrg # POSIX mkdir -p sets u+wx bits regardless of umask, which 34521c2f794Smrg # is incompatible with FreeBSD 'install' when (umask & 300) != 0. 34621c2f794Smrg ;; 34721c2f794Smrg *) 34821c2f794Smrg tmpdir=${TMPDIR-/tmp}/ins$RANDOM-$$ 34921c2f794Smrg trap 'ret=$?; rmdir "$tmpdir/d" "$tmpdir" 2>/dev/null; exit $ret' 0 35021c2f794Smrg 35121c2f794Smrg if (umask $mkdir_umask && 35221c2f794Smrg exec $mkdirprog $mkdir_mode -p -- "$tmpdir/d") >/dev/null 2>&1 35321c2f794Smrg then 35421c2f794Smrg if test -z "$dir_arg" || { 35521c2f794Smrg # Check for POSIX incompatibilities with -m. 35621c2f794Smrg # HP-UX 11.23 and IRIX 6.5 mkdir -m -p sets group- or 35721c2f794Smrg # other-writeable bit of parent directory when it shouldn't. 35821c2f794Smrg # FreeBSD 6.1 mkdir -m -p sets mode of existing directory. 35921c2f794Smrg ls_ld_tmpdir=`ls -ld "$tmpdir"` 36021c2f794Smrg case $ls_ld_tmpdir in 36121c2f794Smrg d????-?r-*) different_mode=700;; 36221c2f794Smrg d????-?--*) different_mode=755;; 36321c2f794Smrg *) false;; 36421c2f794Smrg esac && 36521c2f794Smrg $mkdirprog -m$different_mode -p -- "$tmpdir" && { 36621c2f794Smrg ls_ld_tmpdir_1=`ls -ld "$tmpdir"` 36721c2f794Smrg test "$ls_ld_tmpdir" = "$ls_ld_tmpdir_1" 36821c2f794Smrg } 36921c2f794Smrg } 37021c2f794Smrg then posix_mkdir=: 37121c2f794Smrg fi 37221c2f794Smrg rmdir "$tmpdir/d" "$tmpdir" 37321c2f794Smrg else 37421c2f794Smrg # Remove any dirs left behind by ancient mkdir implementations. 37521c2f794Smrg rmdir ./$mkdir_mode ./-p ./-- 2>/dev/null 37621c2f794Smrg fi 37721c2f794Smrg trap '' 0;; 37821c2f794Smrg esac;; 37921c2f794Smrg esac 38021c2f794Smrg 38121c2f794Smrg if 38221c2f794Smrg $posix_mkdir && ( 38321c2f794Smrg umask $mkdir_umask && 38421c2f794Smrg $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir" 38521c2f794Smrg ) 38621c2f794Smrg then : 38721c2f794Smrg else 38821c2f794Smrg 38921c2f794Smrg # The umask is ridiculous, or mkdir does not conform to POSIX, 39021c2f794Smrg # or it failed possibly due to a race condition. Create the 39121c2f794Smrg # directory the slow way, step by step, checking for races as we go. 39221c2f794Smrg 39321c2f794Smrg case $dstdir in 39412391620Smrg /*) prefix='/';; 39582e12b1bSmrg [-=\(\)!]*) prefix='./';; 39612391620Smrg *) prefix='';; 39721c2f794Smrg esac 39821c2f794Smrg 39912391620Smrg eval "$initialize_posix_glob" 40021c2f794Smrg 40121c2f794Smrg oIFS=$IFS 40221c2f794Smrg IFS=/ 40312391620Smrg $posix_glob set -f 40421c2f794Smrg set fnord $dstdir 40521c2f794Smrg shift 40612391620Smrg $posix_glob set +f 40721c2f794Smrg IFS=$oIFS 40821c2f794Smrg 40921c2f794Smrg prefixes= 41021c2f794Smrg 41121c2f794Smrg for d 41221c2f794Smrg do 41382e12b1bSmrg test X"$d" = X && continue 41421c2f794Smrg 41521c2f794Smrg prefix=$prefix$d 41621c2f794Smrg if test -d "$prefix"; then 41721c2f794Smrg prefixes= 41821c2f794Smrg else 41921c2f794Smrg if $posix_mkdir; then 42021c2f794Smrg (umask=$mkdir_umask && 42121c2f794Smrg $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir") && break 42221c2f794Smrg # Don't fail if two instances are running concurrently. 42321c2f794Smrg test -d "$prefix" || exit 1 42421c2f794Smrg else 42521c2f794Smrg case $prefix in 42621c2f794Smrg *\'*) qprefix=`echo "$prefix" | sed "s/'/'\\\\\\\\''/g"`;; 42721c2f794Smrg *) qprefix=$prefix;; 42821c2f794Smrg esac 42921c2f794Smrg prefixes="$prefixes '$qprefix'" 43021c2f794Smrg fi 43121c2f794Smrg fi 43221c2f794Smrg prefix=$prefix/ 43321c2f794Smrg done 43421c2f794Smrg 43521c2f794Smrg if test -n "$prefixes"; then 43621c2f794Smrg # Don't fail if two instances are running concurrently. 43721c2f794Smrg (umask $mkdir_umask && 43821c2f794Smrg eval "\$doit_exec \$mkdirprog $prefixes") || 43921c2f794Smrg test -d "$dstdir" || exit 1 44021c2f794Smrg obsolete_mkdir_used=true 44121c2f794Smrg fi 44221c2f794Smrg fi 44321c2f794Smrg fi 44421c2f794Smrg 44521c2f794Smrg if test -n "$dir_arg"; then 44621c2f794Smrg { test -z "$chowncmd" || $doit $chowncmd "$dst"; } && 44721c2f794Smrg { test -z "$chgrpcmd" || $doit $chgrpcmd "$dst"; } && 44821c2f794Smrg { test "$obsolete_mkdir_used$chowncmd$chgrpcmd" = false || 44921c2f794Smrg test -z "$chmodcmd" || $doit $chmodcmd $mode "$dst"; } || exit 1 45021c2f794Smrg else 45121c2f794Smrg 45221c2f794Smrg # Make a couple of temp file names in the proper directory. 45321c2f794Smrg dsttmp=$dstdir/_inst.$$_ 45421c2f794Smrg rmtmp=$dstdir/_rm.$$_ 45521c2f794Smrg 45621c2f794Smrg # Trap to clean up those temp files at exit. 45721c2f794Smrg trap 'ret=$?; rm -f "$dsttmp" "$rmtmp" && exit $ret' 0 45821c2f794Smrg 45921c2f794Smrg # Copy the file name to the temp name. 46021c2f794Smrg (umask $cp_umask && $doit_exec $cpprog "$src" "$dsttmp") && 46121c2f794Smrg 46221c2f794Smrg # and set any options; do chmod last to preserve setuid bits. 46321c2f794Smrg # 46421c2f794Smrg # If any of these fail, we abort the whole thing. If we want to 46521c2f794Smrg # ignore errors from any of these, just make sure not to ignore 46621c2f794Smrg # errors from the above "$doit $cpprog $src $dsttmp" command. 46721c2f794Smrg # 46812391620Smrg { test -z "$chowncmd" || $doit $chowncmd "$dsttmp"; } && 46912391620Smrg { test -z "$chgrpcmd" || $doit $chgrpcmd "$dsttmp"; } && 47012391620Smrg { test -z "$stripcmd" || $doit $stripcmd "$dsttmp"; } && 47112391620Smrg { test -z "$chmodcmd" || $doit $chmodcmd $mode "$dsttmp"; } && 47212391620Smrg 47312391620Smrg # If -C, don't bother to copy if it wouldn't change the file. 47412391620Smrg if $copy_on_change && 47512391620Smrg old=`LC_ALL=C ls -dlL "$dst" 2>/dev/null` && 47612391620Smrg new=`LC_ALL=C ls -dlL "$dsttmp" 2>/dev/null` && 47712391620Smrg 47812391620Smrg eval "$initialize_posix_glob" && 47912391620Smrg $posix_glob set -f && 48012391620Smrg set X $old && old=:$2:$4:$5:$6 && 48112391620Smrg set X $new && new=:$2:$4:$5:$6 && 48212391620Smrg $posix_glob set +f && 48312391620Smrg 48412391620Smrg test "$old" = "$new" && 48512391620Smrg $cmpprog "$dst" "$dsttmp" >/dev/null 2>&1 48612391620Smrg then 48712391620Smrg rm -f "$dsttmp" 48812391620Smrg else 48912391620Smrg # Rename the file to the real destination. 49012391620Smrg $doit $mvcmd -f "$dsttmp" "$dst" 2>/dev/null || 49112391620Smrg 49212391620Smrg # The rename failed, perhaps because mv can't rename something else 49312391620Smrg # to itself, or perhaps because mv is so ancient that it does not 49412391620Smrg # support -f. 49512391620Smrg { 49612391620Smrg # Now remove or move aside any old file at destination location. 49712391620Smrg # We try this two ways since rm can't unlink itself on some 49812391620Smrg # systems and the destination file might be busy for other 49912391620Smrg # reasons. In this case, the final cleanup might fail but the new 50012391620Smrg # file should still install successfully. 50112391620Smrg { 50212391620Smrg test ! -f "$dst" || 50312391620Smrg $doit $rmcmd -f "$dst" 2>/dev/null || 50412391620Smrg { $doit $mvcmd -f "$dst" "$rmtmp" 2>/dev/null && 50512391620Smrg { $doit $rmcmd -f "$rmtmp" 2>/dev/null; :; } 50612391620Smrg } || 50712391620Smrg { echo "$0: cannot unlink or rename $dst" >&2 50812391620Smrg (exit 1); exit 1 50912391620Smrg } 51012391620Smrg } && 51112391620Smrg 51212391620Smrg # Now rename the file to the real destination. 51312391620Smrg $doit $mvcmd "$dsttmp" "$dst" 51412391620Smrg } 51512391620Smrg fi || exit 1 51621c2f794Smrg 51721c2f794Smrg trap '' 0 51821c2f794Smrg fi 51921c2f794Smrgdone 52021c2f794Smrg 52121c2f794Smrg# Local variables: 52221c2f794Smrg# eval: (add-hook 'write-file-hooks 'time-stamp) 52321c2f794Smrg# time-stamp-start: "scriptversion=" 52421c2f794Smrg# time-stamp-format: "%:y-%02m-%02d.%02H" 52512391620Smrg# time-stamp-time-zone: "UTC" 52612391620Smrg# time-stamp-end: "; # UTC" 52721c2f794Smrg# End: 528