i.scsivhciconf revision 7c478bd95313f5f23a4c958a745db2134aa03244
#!/bin/sh
#
# CDDL HEADER START
#
# The contents of this file are subject to the terms of the
# Common Development and Distribution License, Version 1.0 only
# (the "License"). You may not use this file except in compliance
# with the License.
#
# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
# or http://www.opensolaris.org/os/licensing.
# See the License for the specific language governing permissions
# and limitations under the License.
#
# When distributing Covered Code, include this CDDL HEADER in each
# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
# If applicable, add the following below this CDDL HEADER, with the
# fields enclosed by brackets "[]" replaced with your own identifying
# information: Portions Copyright [yyyy] [name of copyright owner]
#
# CDDL HEADER END
#
#
# ident "%Z%%M% %I% %E% SMI"
#
# Copyright 2004 Sun Microsystems, Inc. All rights reserved.
# Use is subject to license terms.
#
PATH=/usr/bin:/usr/sbin:$PATH; export PATH
PREFIX=/tmp/scsi_vhci.$$
FPCONF=kernel/drv/fp.conf
#
# Add any new entries to be added to fp.conf to this file. The class action
# script for fp.conf will append the entries of this file to fp.conf.
#
NEW_FPCONF_ENTRIES=/tmp/fp.conf.new_entries
#
# Check if mpxio is enabled or disabled in the given scsi_vhci.conf file
# $1 scsi_vhci.conf file
#
# Returns 0 if disabled, 1 if enabled, 2 if can't determine.
#
is_mpxio_enabled()
{
if egrep "^[ ]*mpxio-disable[ ]*=[ ]*\"yes\"[ ]*;" \
$1 > /dev/null 2>&1; then
return 0
fi
if egrep "^[ ]*mpxio-disable[ ]*=[ ]*\"no\"[ ]*;" \
$1 > /dev/null 2>&1; then
return 1
fi
return 2
}
#
# Make sed script to do most of the work of upgrading scsi_vhci.conf.
#
make_sed_script()
{
#
# remove mpxio-disable and forceattach properties.
# forceattach is no longer necessary as the framework always loads
# scsi_vhci early during boot.
#
cat > $SEDSCRIPT << EOF
/^# mpxio Global enable\/disable configuration$/d
/^# possible values are mpxio-disable="no" or mpxio-disable="yes"$/d
/^# mpxio global enable\/disable switch: setting mpxio-disable="no" will activate$/d
/^# I\/O multipathing; setting mpxio-disable="yes" disables this feature (do$/d
/^# not remove this property).$/d
/^[ ]*mpxio-disable[ ]*=/d
/^# Force load driver to support hotplug activity (do not remove this property).$/d
/^ddi-forceattach=1;$/d
EOF
}
#
# Upgrade the destination scsi_vhci.conf file.
# $1 source scsi_vhci.conf file
# $2 destination scsi_vhci.conf file (the file to be upgraded)
#
# Returns 0 on success, non zero on failure.
#
update_scsi_vhci()
{
TMPSCSIVHCI=$PREFIX.conf
SEDSCRIPT=$PREFIX.sed
NEWIDENT1=$PREFIX.ident1
NEWIDENT2=$PREFIX.ident2
# make sed script to do most of the work of upgrading
make_sed_script
# make sed script to replace old ident with new ident
IDENT="^#.*ident.*SMI\"$"
if grep "$IDENT" $1 > $NEWIDENT1 2>/dev/null; then
# replace / by \/
sed "s/\\//\\\\\\//g" $NEWIDENT1 > $NEWIDENT2 2>/dev/null
echo "s/$IDENT/`cat $NEWIDENT2`/" >> $SEDSCRIPT
fi
sed -f $SEDSCRIPT $2 > $TMPSCSIVHCI 2>/dev/null
retval=$?
if [ $retval -eq 0 ]; then
cp $TMPSCSIVHCI $2
fi
rm -f $NEWIDENT1 $NEWIDENT2 $SEDSCRIPT $TMPSCSIVHCI
return $retval
}
#
# Preprocess a driver.conf file. The output is written to out file.
# $1 driver.conf file
# $2 out file
#
preprocess()
{
TMPPREPROCESS=$PREFIX.preprocess
# strip comments, blank lines, leading and trailing spaces
sed -e "/^[ ]*#/d" \
-e "/^[ ]*$/d" \
-e "s/^[ ]*//" \
-e "s/[ ]*$//" $1 > $TMPPREPROCESS
# combine entries that spawn more than one line
sed -e "/;$/p" \
-e "/;$/d" \
-e ":rdnext" \
-e "N" \
-e "s/\n/ /" \
-e "/;$/p" \
-e "/;$/d" \
-e "b rdnext" $TMPPREPROCESS > $2
rm -f $TMPPREPROCESS
}
#
# Disable mpxio on all fp ports.
# $1 fp.conf file
#
# Returns 0 on success, non zero on failure.
#
disable_mpxio_globally()
{
TMPFP1=$PREFIX.fp1
TMPFP2=$PREFIX.fp2
if [ ! -f $1 ]; then
echo "mpxio-disable=\"yes\";" > $NEW_FPCONF_ENTRIES
return 0
fi
#
# change all occurrences of mpxio-disable (including per port) value
# from "no" to "yes" except in comments.
#
sed -e "/^[ ]*#/p" -e "/^[ ]*#/d" \
-e "s/mpxio-disable[ ]*=[ ]*\"no\"/mpxio-disable=\"yes\"/g"\
$1 > $TMPFP1 2>/dev/null
retval=$?
if [ $retval -eq 0 ]; then
preprocess $TMPFP1 $TMPFP2
# add global mpxio-disable if not already present
egrep "^mpxio-disable[ ]*=[ ]*\"yes\"[ ]*;" \
$TMPFP2 >/dev/null 2>&1
if [ $? -ne 0 ]; then
echo "mpxio-disable=\"yes\";" > $NEW_FPCONF_ENTRIES
fi
cp $TMPFP1 $1
rm -f $TMPFP2
fi
rm -f $TMPFP1
return $retval
}
#
# Check if mpxio-disable entry is present in fp.conf file for the specified
# controller and port.
#
# $1 fp.conf file
# $2 controller name
# $3 port number
#
# Returns 1 if the entry is present, 0 if not.
#
check_mpxio()
{
TMPFILE=$PREFIX.check
preprocess $1 $TMPFILE
if egrep "parent[ ]*=[ ]*\"$2\"" $TMPFILE \
2>/dev/null | egrep "port[ ]*=[ ]*$3" 2>/dev/null | \
egrep "mpxio-disable[ ]*=[ ]*\".*\"" >/dev/null 2>&1; then
rm -f $TMPFILE
return 1
fi
rm -f $TMPFILE
return 0
}
#
# Reads vfstab entry fields corresponding to the specified mount point.
# This function assumes that stdin is already set to vfstab.
#
# $1 mount point
#
readvfstab()
{
while read special fsckdev mountp fstype fsckpass automnt mntopts; do
case "$special" in
'#'* | '') # Ignore comments, empty lines
continue ;;
'-') # Ignore no-action lines
continue
esac
[ "x$mountp" = "x$1" ] && break
done
}
#
# Disable mpxio on the specified controller if the controller had mpxio
# disabled (implicitly) before the upgrade.
#
# $1 directory on which the root filesystem of the OS image being
# upgraded is mounted.
# $2 /dev link or /devices name of the root slice whose controller needs
# to have mpxio disabled.
#
disable_mpxio()
{
if echo "$2" | grep "/devices/" >/dev/null 2>&1; then
physpath=`echo "$2" | sed "s/^.*\/devices\//\//" 2>/dev/null`
elif echo "$2" | grep "/dev/" >/dev/null 2>&1; then
# it is /dev link
physpath=`ls -l $1/$2 | sed "s/^.*\/devices\//\//" 2>/dev/null`
else
return
fi
if echo "$physpath" | grep "/fp@" >/dev/null 2>&1; then
# extract controller and port number
controller=`echo "$physpath" | sed "s/\/fp@.*$//" 2>/dev/null`
port=`echo "$physpath" | sed -e "s/^.*\/fp@//" 2>/dev/null \
-e "s/,0\/.*$//" 2>/dev/null`
#
# add an entry to fp.conf to disable mpxio only if not already
# present.
#
check_mpxio $1/$FPCONF $controller $port
if [ $? -eq 0 ]; then
echo "name=\"fp\" parent=\"$controller\" port=$port \
mpxio-disable=\"yes\";" >> $NEW_FPCONF_ENTRIES
fi
fi
}
#
# Disable mpxio on the root controller if it was implicitly disabled before
# the upgrade.
#
# Note that s8 and s9 didn't have mpxio support on the root controller.
# So root controller always had mpxio disabled. But Network Storage supplies a
# patch to enable mpxio on the root controller.
#
# $1 directory on which the root filesystem of the OS image being
# upgraded is mounted.
#
disable_mpxio_on_root()
{
rel=`uname -r | cut -f 2 -d .`
if [ $rel -lt 10 ]; then
# live upgrade
root=/
else
root=$1
fi
#
# if the root is a metadevice disable mpxio on each of the component
# controllers if the component controller had mpxio disabled before.
#
if mount | grep "^$root on /dev/md/dsk/" >/dev/null 2>&1; then
metadev=`mount | grep "^$root on /dev/md/dsk/" | \
cut -f3 -d " " | cut -f5 -d "/"`
devlist=`metastat -p $metadev | grep " 1 1 " | \
sed -e "s/^.* 1 1 //" | cut -f1 -d " "`
if [ "x$devlist" = x ]; then
return
fi
for d in $devlist
do
disable_mpxio $1 /dev/dsk/$d
done
else
exec < ${root}/etc/vfstab; readvfstab "/"
disable_mpxio $1 $special
fi
}
if read src dest; then
# first delete if a stale version of this file exists
rm -f $NEW_FPCONF_ENTRIES
if [ ! -f $dest ]; then
cp $src $dest
#
# If we are upgrading from s7 or s8, scsi_vhci.conf file
# won't exist and mpxio needs to be globally disabled.
#
# XXX Install doesn't provide a way to distinguish between
# fresh install and upgrade. In this hack we assume that if
# the system's vfstab already contains an entry for the root
# it must be an upgrade.
#
if [ -s $PKG_INSTALL_ROOT/etc/vfstab ]; then
exec < $PKG_INSTALL_ROOT/etc/vfstab; readvfstab "/"
if [ "x$mountp" = x/ ]; then
disable_mpxio_globally $PKG_INSTALL_ROOT/$FPCONF
if [ $? -ne 0 ]; then
exit 1
fi
fi
fi
exit 0
fi
is_mpxio_enabled $dest
mpxio_on=$?
update_scsi_vhci $src $dest
if [ $? -ne 0 ]; then
exit 1
fi
if [ $mpxio_on -eq 0 ]; then
disable_mpxio_globally $PKG_INSTALL_ROOT/$FPCONF
if [ $? -ne 0 ]; then
exit 1
fi
elif [ $mpxio_on -eq 1 ]; then
if [ "x$PKG_INSTALL_ROOT" != x ]; then
disable_mpxio_on_root $PKG_INSTALL_ROOT
else
disable_mpxio_on_root /
fi
fi
fi
exit 0