diff options
Diffstat (limited to 'source/a/pkgtools/scripts/installpkg')
-rw-r--r-- | source/a/pkgtools/scripts/installpkg | 327 |
1 files changed, 227 insertions, 100 deletions
diff --git a/source/a/pkgtools/scripts/installpkg b/source/a/pkgtools/scripts/installpkg index 96c34fd9..87a7f57a 100644 --- a/source/a/pkgtools/scripts/installpkg +++ b/source/a/pkgtools/scripts/installpkg @@ -1,7 +1,7 @@ #!/bin/sh # Copyright 1994, 1998, 2000 Patrick Volkerding, Concord, CA, USA # Copyright 2001, 2003 Slackware Linux, Inc., Concord, CA, USA -# Copyright 2007, 2009, 2011 Patrick Volkerding, Sebeka, MN, USA +# Copyright 2007, 2009, 2011, 2017, 2018 Patrick Volkerding, Sebeka, MN, USA # All rights reserved. # # Redistribution and use of this script, with or without modification, is @@ -21,6 +21,33 @@ # OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF # ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. # +# Thu May 24 20:23:55 UTC 2018 +# Added --terselength option to set the line length in --terse mode. +# Allow adding NOLOCK in an install script to allow it to run without locking. +# +# Sat May 19 22:42:03 UTC 2018 +# Implement locking to prevent screen output or install script collisions if +# multiple copies of installpkg are running simultaneously. +# Use ${MCOOKIE} instead of $$ (might as well, since we already generated it). +# +# Tue Apr 17 17:26:44 UTC 2018 +# Quit with the funny business in /install. Note however that /install still +# isn't a safe directory to use in a package for anything other than package +# metadata. Other files placed there are going to be left on the system in +# /installpkg-$(mcookie). That could be worked around, but we'll wait until +# someone reports there is a need. The main reason to do this is that /install +# was a collision point if more than one copy of installpkg was running at +# once. With this change, the pkgtools are (more or less) thread-safe. +# +# Tue Feb 13 01:19:46 UTC 2018 +# Use recent tar, and support restoring POSIX ACLs and extended attributes. +# +# Tue Dec 12 21:49:48 UTC 2017 +# If possible, use multiple decompression threads. +# +# Thu Dec 7 04:09:17 UTC 2017 +# Change meaning of .tlz to tar.lz (lzip) +# # Sun Sep 6 21:58:36 BST 2009 # Replaced usage of "cat" with STDIN redirection or file name parameters # to speed up execution on ARM. @@ -58,13 +85,6 @@ # Changed $TMP directory to /var/log/setup/tmp, and chmod'ed it 700 to close # some security holes. -# A stronger formula is needed to regularize output that will be parsed. -unset LANG LC_CTYPE LC_NUMERIC LC_TIME LC_COLLATE LC_MONETARY \ - LC_MESSAGES LC_PAPER LC_NAME LC_ADDRESS LC_TELEPHONE LC_MEASUREMENT \ - LC_IDENTIFICATION LC_ALL -LANG=C -export LANG - # Return a package name that has been stripped of the dirname portion # and any of the valid extensions (only): pkgbase() { @@ -88,21 +108,27 @@ MD5SUM=0 # So that we know what to expect... umask 022 -TAR=tar-1.13 -$TAR --help 1> /dev/null 2> /dev/null -if [ ! $? = 0 ]; then - TAR=tar -fi -if [ ! "$(LC_MESSAGES=C $TAR --version)" = "tar (GNU tar) 1.13 -Copyright (C) 1988, 92,93,94,95,96,97,98, 1999 Free Software Foundation, Inc. -This is free software; see the source for copying conditions. There is NO -warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. +# If we have mcookie and a tar that is recent enough to support --transform, +# then we can stop needlessly erasing files in the /install directory while +# also making installpkg thread-safe. Don't check for recent tar - we'll +# already break from --attrs and --xattrs anyway if the wrong tar is used. +if which mcookie 1> /dev/null 2> /dev/null ; then + MCOOKIE=$(mcookie) + INSTDIR=installpkg-${MCOOKIE} +else + # Well, we will make due with this: + MCOOKIE=$$ + INSTDIR=installpkg-${MCOOKIE} +fi -Written by John Gilmore and Jay Fenlason." ]; then - echo "WARNING: pkgtools are unstable with tar > 1.13." - echo " You should provide a \"tar-1.13\" in your \$PATH." - sleep 5 +# Create a lockfile directory if it doesn't exist. We can use it to prevent +# screen corruption (from multiple dialogs) and install script collisions +# (from multiple scripts trying to work on the same files) in the case of +# parallel instances of installpkg. +INSTLOCKDIR=${INSTLOCKDIR:-/run/installpkg-lock} +if [ ! -d $INSTLOCKDIR ]; then + mkdir -p $INSTLOCKDIR fi usage() { @@ -116,16 +142,24 @@ options: --warn (warn if files will be overwritten, but do not install) --root /mnt (install someplace else, like /mnt) --infobox (use dialog to draw an info box) --terse (display a one-line short description for install) + --terselength <length> (line length in terse mode - default is + the number of columns available) --menu (confirm package installation with a menu, unless the priority is [required] or ADD) --ask (used with menu mode: always ask if a package should be installed regardless of what the package's priority is) - --priority ADD|REC|OPT|SKP (provide a priority for the entire + --priority ADD|REC|OPT|SKP (provide a priority for the entire package list to use instead of the priority in the tagfile) --tagfile /somedir/tagfile (specify a different file to use - for package priorities. The default is "tagfile" in + for package priorities. The default is "tagfile" in the package's directory) + --threads <number> For xz/plzip compressed packages, set the max + number of threads to be used for decompression. Only has + an effect if a multithreaded compressor was used, and then + only on large packages. For plzip, the default is equal to + the number of CPU threads available on the machine. For xz, + the default is equal to 2. --md5sum (record the package's md5sum in the metadata file) EOF @@ -143,6 +177,17 @@ package_name() { pkgbase $1 | sed 's?-[^-]*-[^-]*-[^-]*$??' } +# Set maximum number of threads to use. By default, this will be the number +# of CPU threads: +THREADS="$(nproc)" + +# Set default line length for terse mode: +if which tput 1> /dev/null 2> /dev/null ; then + TERSELENGTH=$(tput cols) +else + TERSELENGTH=80 +fi + # Parse options: MODE=install # standard text-mode while [ 0 ]; do @@ -158,6 +203,9 @@ while [ 0 ]; do elif [ "$1" = "-terse" -o "$1" = "--terse" ]; then MODE=terse shift 1 + elif [ "$1" = "-terselength" -o "$1" = "--terselength" ]; then + TERSELENGTH=$2 + shift 2 elif [ "$1" = "-menu" -o "$1" = "--menu" ]; then MODE=menu shift 1 @@ -174,6 +222,12 @@ while [ 0 ]; do exit fi shift 2 + elif [ "$1" = "-threads" -o "$1" = "--threads" ]; then + THREADS="$2" + shift 2 + # xz has not yet implemented multi-threaded decompression. + # Who knows if or how well it will work... + XZ_THREADS_FORCED=yes elif [ "$1" = "-priority" -o "$1" = "--priority" ]; then if [ "$2" = "" ]; then usage @@ -222,41 +276,56 @@ fi # If -warn mode was requested, produce the output and then exit: if [ "$MODE" = "warn" ]; then while [ -f "$1" ]; do - mkdir -p $TMP/scan$$ + mkdir -p $TMP/scan${MCOOKIE} # Determine extension: packageext="$( echo $1 | rev | cut -f 1 -d . | rev)" - # Determine compressor utility: + # Determine decompressor utility: case $packageext in 'tgz' ) packagecompression=gzip ;; 'tbz' ) - packagecompression=bzip2 + if which lbzip2 1> /dev/null 2> /dev/null ; then + packagecompression=lbzip2 + else + packagecompression=bzip2 + fi ;; 'tlz' ) - packagecompression=lzma + if which plzip 1> /dev/null 2> /dev/null ; then + packagecompression="plzip --threads=${THREADS}" + elif which lzip 1> /dev/null 2> /dev/null ; then + packagecompression=lzip + else + echo "ERROR: lzip compression utility not found in \$PATH." + exit 3 + fi ;; 'txz' ) - packagecompression=xz + if [ ! "$XZ_THREADS_FORCED" = "yes" ]; then + packagecompression="xz --threads=${THREADS}" + else + packagecompression="xz --threads=2" + fi ;; esac - ( cd $TMP/scan$$ ; $packagecompression -dc | $TAR xf - install ) < $1 2> /dev/null - if [ -r $TMP/scan$$/install/doinst.sh ]; then - if grep ' rm -rf ' $TMP/scan$$/install/doinst.sh 1>/dev/null 2>/dev/null ; then - grep ' rm -rf ' $TMP/scan$$/install/doinst.sh > $TMP/scan$$/install/delete - for f in `cat $TMP/scan$$/install/delete | cut -f 3,7 -d ' ' | tr ' ' '/'`; do + ( cd $TMP/scan${MCOOKIE} ; $packagecompression -dc | tar xf - install ) < $1 2> /dev/null + if [ -r $TMP/scan${MCOOKIE}/install/doinst.sh ]; then + if grep ' rm -rf ' $TMP/scan${MCOOKIE}/install/doinst.sh 1>/dev/null 2>/dev/null ; then + grep ' rm -rf ' $TMP/scan${MCOOKIE}/install/doinst.sh > $TMP/scan${MCOOKIE}/install/delete + for f in `cat $TMP/scan${MCOOKIE}/install/delete | cut -f 3,7 -d ' ' | tr ' ' '/'`; do f="/$f" if [ -f "$f" -o -L "$f" ]; then echo "$f" fi done fi - if [ -d $TMP/scan$$ ]; then - ( cd $TMP/scan$$ ; rm -rf install ) 2> /dev/null - ( cd $TMP ; rmdir scan$$ ) 2> /dev/null + if [ -d $TMP/scan${MCOOKIE} ]; then + ( cd $TMP/scan${MCOOKIE} ; rm -rf install ) 2> /dev/null + ( cd $TMP ; rmdir scan${MCOOKIE} ) 2> /dev/null fi fi - for f in `( $packagecompression -dc | $TAR tf - ) < $1 | grep -v 'drwx'`; do + for f in `( $packagecompression -dc | tar tf - ) < $1 | grep -v 'drwx'`; do f="/$f" if [ -f "$f" -o -L "$f" ]; then echo "$f" @@ -304,18 +373,33 @@ for package in $* ; do packagecompression=gzip ;; 'tbz' ) - packagecompression=bzip2 + if which lbzip2 1> /dev/null 2> /dev/null ; then + packagecompression=lbzip2 + else + packagecompression=bzip2 + fi ;; 'tlz' ) - packagecompression=lzma + if which plzip 1> /dev/null 2> /dev/null ; then + packagecompression="plzip --threads=${THREADS}" + elif which lzip 1> /dev/null 2> /dev/null ; then + packagecompression=lzip + else + echo "ERROR: lzip compression utility not found in \$PATH." + exit 3 + fi ;; 'txz' ) - packagecompression=xz + if [ ! "$XZ_THREADS_FORCED" = "yes" ]; then + packagecompression="xz --threads=${THREADS}" + else + packagecompression="xz --threads=2" + fi ;; esac # Test presence of external compression utility: - if ! $packagecompression --help 1> /dev/null 2> /dev/null ; then + if ! $(echo $packagecompression | cut -f 1 -d ' ') --help 1> /dev/null 2> /dev/null ; then EXITSTATUS=5 if [ "$MODE" = "install" ]; then echo "Cannot install $package: external compression utility $packagecompression missing" @@ -375,28 +459,38 @@ for package in $* ; do if [ "$MODE" = "install" ]; then echo "Verifying package $(basename $package)." fi - cat $package | $packagecompression -dc | dd 2> $TMP/tmpsize$$ | $TAR tf - 1> $TMP/tmplist$$ 2> /dev/null + # The stray cat reduces the frequency of the lack of reported size. + # If it still fails, we hit it with a bigger hammer down below. + cat $package | $packagecompression -dc | LC_ALL=C dd 2> $TMP/tmpsize${MCOOKIE} | cat | tar tf - 2> /dev/null 1> $TMP/tmplist${MCOOKIE} TARERROR=$? if [ ! "$TARERROR" = "0" ]; then EXITSTATUS=1 # tar file corrupt if [ "$MODE" = "install" ]; then echo "Unable to install $package: tar archive is corrupt (tar returned error code $TARERROR)" fi - rm -f $TMP/tmplist$$ $TMP/tmpsize$$ + rm -f $TMP/tmplist${MCOOKIE} $TMP/tmpsize${MCOOKIE} continue fi - UNCOMPRESSED="$(cat $TMP/tmpsize$$ | tail -n 1 | cut -f 1 -d ' ' | numfmt --to=iec)" - rm -f $TMP/tmpsize$$ + UNCOMPRESSED="$(cat $TMP/tmpsize${MCOOKIE} | tail -n 1 | cut -f 1 -d ' ' | numfmt --to=iec)" + # Weird bug "fix". Sometimes we get no uncompressed size (this started when we + # moved away from tar-1.13, but I don't see what that could have to do with + # it). So, if we have no uncompressed size here, demand it in this loop. + # Hopefully the bug is not weird enough to make this an infinite loop. :/ + while [ "$UNCOMPRESSED" = "" ]; do + cat $package | $packagecompression -dc | LC_ALL=C dd 1> /dev/null 2> $TMP/tmpsize${MCOOKIE} + UNCOMPRESSED="$(cat $TMP/tmpsize${MCOOKIE} | tail -n 1 | cut -f 1 -d ' ' | numfmt --to=iec)" + done + rm -f $TMP/tmpsize${MCOOKIE} # If we still don't have a package description, look inside the package. # This requires a costly untar. if [ "$DESCRIPTION" = "" ]; then - mkdir -p $TMP/scan$$ - ( cd $TMP/scan$$ ; $packagecompression -dc | $TAR xf - install ) < $package 2> /dev/null - if grep "^$packagebase:" "$TMP/scan$$/install/slack-desc" 1> /dev/null 2> /dev/null ; then - DESCRIPTION="$TMP/scan$$/install/slack-desc" - elif grep "^$shortname:" "$TMP/scan$$/install/slack-desc" 1> /dev/null 2> /dev/null ; then - DESCRIPTION="$TMP/scan$$/install/slack-desc" + mkdir -p $TMP/scan${MCOOKIE} + ( cd $TMP/scan${MCOOKIE} ; $packagecompression -dc | tar xf - install ) < $package 2> /dev/null + if grep "^$packagebase:" "$TMP/scan${MCOOKIE}/install/slack-desc" 1> /dev/null 2> /dev/null ; then + DESCRIPTION="$TMP/scan${MCOOKIE}/install/slack-desc" + elif grep "^$shortname:" "$TMP/scan${MCOOKIE}/install/slack-desc" 1> /dev/null 2> /dev/null ; then + DESCRIPTION="$TMP/scan${MCOOKIE}/install/slack-desc" fi fi @@ -406,20 +500,20 @@ for package in $* ; do fi # Gather package infomation into a temporary file: - grep "^$packagebase:" $DESCRIPTION | cut -f 2- -d : | cut -b2- 1> $TMP/tmpmsg$$ 2> /dev/null + grep "^$packagebase:" $DESCRIPTION | cut -f 2- -d : | cut -b2- 1> $TMP/tmpmsg${MCOOKIE} 2> /dev/null if [ "$shortname" != "$packagebase" ]; then - grep "^$shortname:" $DESCRIPTION | cut -f 2- -d : | cut -b2- 1>> $TMP/tmpmsg$$ 2> /dev/null + grep "^$shortname:" $DESCRIPTION | cut -f 2- -d : | cut -b2- 1>> $TMP/tmpmsg${MCOOKIE} 2> /dev/null fi # Adjust the length here. This allows a slack-desc to be any size up to 13 lines instead of fixed at 11. - LENGTH=$(wc -l < $TMP/tmpmsg$$ ) + LENGTH=$(wc -l < $TMP/tmpmsg${MCOOKIE} ) while [ $LENGTH -lt 12 ]; do - echo >> $TMP/tmpmsg$$ + echo >> $TMP/tmpmsg${MCOOKIE} LENGTH=$(expr $LENGTH + 1) done - echo "Size: Compressed: ${COMPRESSED}, uncompressed: ${UNCOMPRESSED}." >> $TMP/tmpmsg$$ + echo "Size: Compressed: ${COMPRESSED}, uncompressed: ${UNCOMPRESSED}." >> $TMP/tmpmsg${MCOOKIE} # For recent versions of dialog it is necessary to add \n to the end of each line # or it will remove repeating spaces and mess up our careful formatting: - cat << EOF > $TMP/controlns$$ + cat << EOF > $TMP/controlns${MCOOKIE} \n \n \n @@ -434,9 +528,9 @@ for package in $* ; do \n \n EOF - paste -d "" $TMP/tmpmsg$$ $TMP/controlns$$ > $TMP/pasted$$ - rm -f $TMP/controlns$$ - mv $TMP/pasted$$ $TMP/tmpmsg$$ + paste -d "" $TMP/tmpmsg${MCOOKIE} $TMP/controlns${MCOOKIE} > $TMP/pasted${MCOOKIE} + rm -f $TMP/controlns${MCOOKIE} + mv $TMP/pasted${MCOOKIE} $TMP/tmpmsg${MCOOKIE} # Emit information to the console: if [ "$MODE" = "install" ]; then if [ "$PMSG" = "" ]; then @@ -450,23 +544,33 @@ EOF grep "^$shortname:" $DESCRIPTION | uniq | sed "s/^$shortname:/#/g" fi elif [ "$MODE" = "terse" ]; then # emit a single description line - printf "%-72s %-6s\n" "$(echo $shortname: $(echo $(cat $DESCRIPTION | grep "^$packagebase:" | sed "s/^$packagebase: //g" | head -n 1 | tr -d '()' | sed "s/^$packagebase //g" ) $(echo " ......................................................................")) | cut -b1-72)" "[${UNCOMPRESSED}]" | cut -b1-80 + ( flock 9 || exit 11 + printf "%-$(expr $TERSELENGTH - 7)s %-6s\n" "$(echo $shortname: $(echo $(cat $DESCRIPTION | grep "^$packagebase:" | sed "s/^$packagebase: //g" | head -n 1 | tr -d '()' | sed "s/^$packagebase //g" ) $(echo " $(printf '.%.0s' {1..256})")) | cut -b1-$(expr $TERSELENGTH - 7))" "$(printf "[%4s]" $UNCOMPRESSED)" + ) 9> $INSTLOCKDIR/dialog.lock elif [ "$MODE" = "infobox" ]; then # install infobox package - dialog --title "Installing package $shortname $PMSG" --infobox "$(cat $TMP/tmpmsg$$)" 0 0 + ( flock 9 || exit 11 + dialog --title "Installing package $shortname $PMSG" --infobox "$(cat $TMP/tmpmsg${MCOOKIE})" 0 0 + ) 9> $INSTLOCKDIR/dialog.lock elif [ "$MODE" = "menu" -a "$PRIORITY" = "ADD" -a ! "$ALWAYSASK" = "yes" ]; then # ADD overrides menu mode unless -ask was used - dialog --title "Installing package $shortname $PMSG" --infobox "$(cat $TMP/tmpmsg$$)" 0 0 + ( flock 9 || exit 11 + dialog --title "Installing package $shortname $PMSG" --infobox "$(cat $TMP/tmpmsg${MCOOKIE})" 0 0 + ) 9> $INSTLOCKDIR/dialog.lock elif [ "$MODE" = "menu" -a "$USERPRIORITY" = "ADD" ]; then # install no matter what $PRIORITY - dialog --title "Installing package $shortname $PMSG" --infobox "$(cat $TMP/tmpmsg$$)" 0 0 + ( flock 9 || exit 11 + dialog --title "Installing package $shortname $PMSG" --infobox "$(cat $TMP/tmpmsg${MCOOKIE})" 0 0 + ) 9> $INSTLOCKDIR/dialog.lock else # we must need a full menu: - dialog --title "Package Name: $shortname $PMSG" --menu "$(cat $TMP/tmpmsg$$)" 0 0 3 \ - "Yes" "Install package $shortname" \ - "No" "Do not install package $shortname" \ - "Quit" "Abort software installation completely" 2> $TMP/reply$$ - if [ ! $? = 0 ]; then - echo "No" > $TMP/reply$$ - fi - REPLY="$(cat $TMP/reply$$)" - rm -f $TMP/reply$$ $TMP/tmpmsg$$ + ( flock 9 || exit 11 + dialog --title "Package Name: $shortname $PMSG" --menu "$(cat $TMP/tmpmsg${MCOOKIE})" 0 0 3 \ + "Yes" "Install package $shortname" \ + "No" "Do not install package $shortname" \ + "Quit" "Abort software installation completely" 2> $TMP/reply${MCOOKIE} + if [ ! $? = 0 ]; then + echo "No" > $TMP/reply${MCOOKIE} + fi + ) 9> $INSTLOCKDIR/dialog.lock + REPLY="$(cat $TMP/reply${MCOOKIE})" + rm -f $TMP/reply${MCOOKIE} $TMP/tmpmsg${MCOOKIE} if [ "$REPLY" = "Quit" ]; then exit 99 # EXIT STATUS 99 = ABORT! elif [ "$REPLY" = "No" ]; then @@ -476,12 +580,12 @@ EOF # Make sure there are no symbolic links sitting in the way of # incoming package files: - grep -v "/$" $TMP/tmplist$$ | while read file ; do + grep -v "/$" $TMP/tmplist${MCOOKIE} | while read file ; do if [ -L "$ROOT/$file" ]; then rm -f "$ROOT/$file" fi done - rm -f $TMP/tmplist$$ + rm -f $TMP/tmplist${MCOOKIE} # Write the package file database entry and install the package: echo "PACKAGE NAME: $shortname" > $ADM_DIR/packages/$shortname @@ -498,56 +602,79 @@ EOF grep "^$shortname:" $DESCRIPTION >> $ADM_DIR/packages/$shortname 2> /dev/null fi echo "FILE LIST:" >> $ADM_DIR/packages/$shortname - ( cd $ROOT/ ; $packagecompression -dc | $TAR -xlUpvf - | sort ) < $package >> $TMP/$shortname 2> /dev/null + if [ "$INSTDIR" = "install" ]; then + ( cd $ROOT/ ; $packagecompression -dc | tar --acls --xattrs --xattrs-include='*' --keep-directory-symlink -xpvf - | LC_ALL=C sort ) < $package >> $TMP/$shortname 2> /dev/null + else + ( cd $ROOT/ ; $packagecompression -dc | tar --transform "s,^install$,$INSTDIR," --transform "s,^install/,$INSTDIR/," --acls --xattrs --xattrs-include='*' --keep-directory-symlink -xpvf - | LC_ALL=C sort ) < $package >> $TMP/$shortname 2> /dev/null + fi if [ "$( grep '^\./' $TMP/$shortname | wc -l | tr -d ' ')" = "1" ]; then # Good. We have a package that meets the Slackware spec. cat $TMP/$shortname >> $ADM_DIR/packages/$shortname else # Some dumb bunny built a package with something other than makepkg. Bad! # Oh well. Bound to happen. Par for the course. Fix it and move on... - echo "WARNING: Package has not been created with 'makepkg'" - echo './' >> $ADM_DIR/packages/$shortname - cat $TMP/$shortname >> $ADM_DIR/packages/$shortname + # We'll assume it's just a recent tar with an unfiltered filelist with all + # files prefixed with "./". No guarantees, but this will usually work. + cat $TMP/$shortname | sed '2,$s,^\./,,' >> $ADM_DIR/packages/$shortname fi rm -f $TMP/$shortname - # It's a good idea to make sure those newly installed libraries - # are properly activated for use: - if [ -x /sbin/ldconfig ]; then - /sbin/ldconfig + # It's a good idea to make sure those newly installed libraries are properly + # activated for use, unless ROOT is pointing somewhere else in which case + # running ldconfig on the host system won't make any difference: + if [ "$ROOT" = "" ] && [ -x /sbin/ldconfig ]; then + ( flock 9 || exit 11 + /sbin/ldconfig 2> /dev/null + ) 9> $INSTLOCKDIR/ldconfig.lock fi - if [ -f $ROOT/install/doinst.sh ]; then + if [ -f $ROOT/$INSTDIR/doinst.sh ]; then if [ "$MODE" = "install" ]; then echo "Executing install script for $(basename $package)." fi - # If bash is available, use sed to convert the install script to use pushd/popd - # rather than spawning subshells which is slow on ARM. This will also speed up - # install script processing on any platform. - if [ -x /bin/bash ]; then - ( cd $ROOT/ ; sed -e's?^( cd \([^;]*\);\(.*\) )$?pushd \1 \&\> /dev/null ; \2 ; popd \&\> /dev/null?g ' install/doinst.sh | /bin/bash ; ) - else - ( cd $ROOT/ ; sh install/doinst.sh ; ) + # Don't use locking if the script contains "NOLOCK": + if grep -q NOLOCK $ROOT/$INSTDIR/doinst.sh ; then + # If bash is available, use sed to convert the install script to use pushd/popd + # rather than spawning subshells which is slow on ARM. This will also speed up + # install script processing on any platform. + if [ -x /bin/bash ]; then + cd $ROOT/ ; sed -e's?^( cd \([^;]*\);\(.*\) )$?pushd \1 \&\> /dev/null ; \2 ; popd \&\> /dev/null?g ' $INSTDIR/doinst.sh | /bin/bash + else + cd $ROOT/ ; sh $INSTDIR/doinst.sh + fi + else # use locking + # If bash is available, use sed to convert the install script to use pushd/popd + # rather than spawning subshells which is slow on ARM. This will also speed up + # install script processing on any platform. + if [ -x /bin/bash ]; then + ( flock 9 || exit 11 + cd $ROOT/ ; sed -e's?^( cd \([^;]*\);\(.*\) )$?pushd \1 \&\> /dev/null ; \2 ; popd \&\> /dev/null?g ' $INSTDIR/doinst.sh | /bin/bash + ) 9> $INSTLOCKDIR/doinst.sh.lock + else + ( flock 9 || exit 11 + cd $ROOT/ ; sh $INSTDIR/doinst.sh + ) 9> $INSTLOCKDIR/doinst.sh.lock + fi fi fi # Clean up the mess... - if [ -d $ROOT/install ]; then - if [ -r $ROOT/install/doinst.sh ]; then - cp $ROOT/install/doinst.sh $ADM_DIR/scripts/$shortname + if [ -d $ROOT/$INSTDIR ]; then + if [ -r $ROOT/$INSTDIR/doinst.sh ]; then + cp $ROOT/$INSTDIR/doinst.sh $ADM_DIR/scripts/$shortname chmod 755 $ADM_DIR/scripts/$shortname fi # /install/doinst.sh and /install/slack-* are reserved locations for the package system. - ( cd $ROOT/install ; rm -f doinst.sh slack-* 1> /dev/null 2>&1 ) - rmdir $ROOT/install 1> /dev/null 2>&1 + # Heh, not any more with a recent tar :-) + ( cd $ROOT/$INSTDIR ; rm -f doinst.sh slack-* 1> /dev/null 2>&1 ) + rmdir $ROOT/$INSTDIR 1> /dev/null 2>&1 fi # If we used a scan directory, get rid of it: - if [ -d "$TMP/scan$$" ]; then - rm -rf "$TMP/scan$$" + if [ -d "$TMP/scan${MCOOKIE}" ]; then + rm -rf "$TMP/scan${MCOOKIE}" fi - rm -f $TMP/tmpmsg$$ $TMP/reply$$ + rm -f $TMP/tmpmsg${MCOOKIE} $TMP/reply${MCOOKIE} if [ "$MODE" = "install" ]; then echo "Package $(basename $package) installed." - echo fi done |