- 论坛徽章:
- 7
|
#!/bin/sh
#
# @(#) vxreconstruct v2.1 - A script to recontruct VxVM relocations & hot-sparing
#
# Author: Mike Arnott (Mike.Arnott@Aus.Sun.COM)
#
# Created: Sat Jun 7 13:17:15 EST 1997
#
# Modified: 97/11/19 12:28:40
#
# Generated: 97/11/19 12:28:59
#
# PRESD & POSTSD Array Element Descriptions
# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# 1 diskgroup name
# 2 volume name
# 3 plex name
# 4 plex type
# 5 subdisk name
# 6 VM disk name
# 7 VM disk offset
# 8 subdisk length
# 9 column number (forced to 0 on concatenations)
# 10 plex offset
# 11 plex state
# 12 plex kstate
# 13 subdisk underlying device
#
# DMINFOPRE & DMINFOPOST Array Element Descriptions
# ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
# 1 VM disk name
# 2 physical device
# 3 device type
# 4 private region length
# 5 public region length
# 6 disk state
#
#
# HotSparing Variable Names
# ~~~~~~~~~~~~~~~~~~~~~~~~~
# DMNAME variable holding current diskgroup & VM disk name
# [diskgrp~vmdisk]
# CURRVM current diskgroup & VM disk name [diskgrp~vmdisk]
# CURRPHYS physical disk that currently holds DMNAME [cXtYdZ]
# OLDVM previous VM disk that resided on CURRPHYS
# [diskgrp~vxdisk]
# OLDPHYS physical disk that DMNAME previously resided on [cXtYdZ]
#
#set -xv
# set defaults
PATH=/sbin:/etc:/bin:/usr/sbin:/usr/bin:/usr/ucb ; export PATH
PROG=`basename $0` ; export PROG
PREFAILURE="" ; export PREFAILURE
POSTFAILURE="" ; export POSTFAILURE
DOIT="./vxrevertconfig" ; export DOIT
DATE="`date`" ; export DATE
NOW="/var/tmp/${PROG}.now.$$" ; export NOW
ID="`id | cut -f2 -d\( | cut -f1 -d\)`" ; export ID
SORTTMP="/var/tmp/${PROG}.sorttmp.$$" ; export SORTTMP
VXPRINT="/usr/sbin/vxprint" ; export VXPRINT
VXDCTL="/usr/sbin/vxdctl" ; export VXDCTL
VXREATTACH="/etc/vx/bin/vxreattach" ; export VXREATTACH
LOCALVXPRINT="/var/tmp/${PROG}.vxprint.$$" ; export LOCALVXPRINT
DGTOUSE="[0-z]+" ; export DGTOUSE
VOLTOUSE="[0-z]+" ; export VOLTOUSE
SANITYTMP="/var/tmp/${PROG}.sanitytmp.$$" ; export SANITYTMP
POSTCHECKSUM="" ; export POSTCHECKSUM
HSTMP="`date +%y.%m.%d.%H.%M.%S`" ; export HSTMP
RLTMP="`date +%y.%m.%d.%H.%M.%S`" ; export RLTMP
DEBUG="/dev/null" ; export DEBUG
# check to ensure we are running as root
if [ "${ID}" = "root" ]
then # OK
:
else # exit - we must be root
echo "${PROG}: must be root to use this script"
exit 1
fi
# define functions
CmdUsage() {
# give usage
cat ${LOCALVXPRINT}
# assign the POSTFAILURE file
POSTFAILURE="${LOCALVXPRINT}"
else # there is no local vxprint - error & exit
ShowMsg "no Post.Failure file given & unable to execute ${VXPRINT}"
exit 1
fi
fi
# check to see the files are readable
if [ ! -r "${PREFAILURE}" -o ! -r "${POSTFAILURE}" ]
then # exit
echo "You must give a readable *PRE & POST* failure \"vxprint -ht\" input file!"
exit 1
fi
# checksum the Post.Failure file for checking against the system that DOIT is
# eventually run against ... delete blank lines & leading & trailing spaces/tabs
POSTCHECKSUM="`sed -e '/^[ ]*$/d' -e 's/^[ ]*//g' -e 's/[ ]*$//g' ${POSTFAILURE} | cksum`"
# run in a subshell
(
# do the fix file prologue
cat Hot Spared disks need only to be physically"
echo "\${PROG}: -> replaced with a disk of the same Sun part"
echo "\${PROG}: -> number (for compatible capacity & performance)."
echo "\${PROG}: -> If the replacement disk has not been re-added to"
echo "\${PROG}: -> the VxVM configuration, this script will add it."
echo "\${PROG}: -> If the replacement disk has been re-added to the"
echo "\${PROG}: -> same disk group in the VxVM configuration from"
echo "\${PROG}: -> which it was removed, this script will rename it"
echo "\${PROG}: -> appropriately. If the replacement disk was "
echo "\${PROG}: -> re-added to a different diskgroup to that which it"
echo "\${PROG}: -> was previously removed, this script will fail."
echo "\${PROG}:"
echo "\${PROG}: -> Disks affected by Hot Relocation must be VxVM"
echo "\${PROG}: -> removed, using vxdiskadm ..."
echo "\${PROG}: -> 4 Remove a disk for replacement"
echo "\${PROG}: -> It must then be physically replaced with a disk of"
echo "\${PROG}: -> the same Sun part number (for compatible capacity &"
echo "\${PROG}: -> performance). The disk must then be VxVM replaced,"
echo "\${PROG}: -> using vxdiskadm ..."
echo "\${PROG}: -> 5 Replace a failed or removed disk"
echo "\${PROG}: * All volumes are started & in optimal mode"
echo "\${PROG}: * All plexes are active & in optimal mode"
echo "\${PROG}: Press to start the VxVM reconstruction ... \c"
read VXVMISSTABLE
# show start date
echo "\n\${PROG}: start @ \`date\` \n"
# check that checksum for current VxVM layout is the same as that vxreconstruct
# was run against
POSTCHECKSUM="${POSTCHECKSUM}"
# run vxprint -ht & check the output
if [ -x "${VXPRINT}" ]
then # compare the checksums
THISCHECKSUM="\`vxprint -ht | sed -e '/^[ ]*$/d' -e 's/^[ ]*//g' -e 's/[ ]*$//g' | cksum\`"
export THISCHECKSUM
# compare the two checksums
if [ "\${POSTCHECKSUM}" != "\${THISCHECKSUM}" ]
then # the checksums do not match
echo "\${PROG}: VxVM configuration checksums do not match!"
echo "\${PROG}: The current VxVM configuration is not what "
echo "\${PROG}: \"${PROG}\" was given to analyse."
echo "\${PROG}: Continuing may cause unpredictable results!"
shallicontinue
else # checksums do match
echo "\${PROG}: VxVM configuration checksums match"
fi
else # give warning
echo "\n\${PROG}: unable to compare checksums of configuration given "
echo "\${PROG}: to \"${PROG}\" & current VxVM configuration"
shallicontinue
fi
# ensure the VxVM config is up to date
echo "\n\${PROG}: running \"vxdctl enable\""
${VXDCTL} enable
echo "\${PROG}: running \"vxreattach\"\n"
${VXREATTACH}
# show boundaries of diskgroup/volume confinement
echo "\n\${PROG}: fixing diskgroup(s) matching RegExp \\"${DGTOUSE}\\" "
echo "\${PROG}: fixing volume(s) matching RegExp \\"${VOLTOUSE}\\" \n"
###############################################################################
################# VxVM reconstruction commands start here #####################
###############################################################################
# turn on command expansion
set -x
EOF_PROLOGUE
# do this in nawk
nawk -v PROG="${PROG}" -v DGTOUSE="${DGTOUSE}" -v VOLTOUSE="${VOLTOUSE}" -v PREFAILURE="${PREFAILURE}" -v POSTFAILURE="${POSTFAILURE}" -v SORTTMP="${SORTTMP}" -v HSTMP="${HSTMP}" -v RLTMP="${RLTMP}" -v DEBUG="${DEBUG}" ' BEGIN { MISSINGSDCOUNT=0 ; AFFECTEDDISKCOUNT=0 }
# catch the disk group on the way through
$1 == "dg" { DG_CUR = $2 ; VOL_CUR = "" ; PL_CUR = "" }
# collect the DM name to PHYSICAL disk mapping
$1 == "dm" { # record all the VXVMDISKS & PHYSDISKS we find
# strip off the slice because we dont use it on the
# subdisk line
DEVNAME = $3
gsub(/s[0-9]$/,"",DEVNAME)
ALLVXVMDISKS[DG_CUR"~"$2] = "true"
if ( FILENAME == PREFAILURE ) {
PREVXVMDISKS[DG_CUR"~"$2] = DEVNAME
PREPHYSDISKS[DEVNAME] = DG_CUR"~"$2
} else {
POSTVXVMDISKS[DG_CUR"~"$2] = DEVNAME
POSTPHYSDISKS[DEVNAME] = DG_CUR"~"$2
}
# record the PRE & POST failure VMDISK info
if ( FILENAME == PREFAILURE ) { DMINFOPRE[DG_CUR"~"$2] = DG_CUR "~" $2 "," DEVNAME "," $4 "," $5 "," $6 "," $7 } else { DMINFOPOST[DG_CUR"~"$2] = DG_CUR "~" $2 "," DEVNAME "," $4 "," $5 "," $6 "," $7 }
}
# catch the volume on the way through
$1 == "v" { VOL_CUR = $2
VOL_TYPE = $7
PL_CUR = ""
PL_TYPE = ""
PL_STATE = ""
PL_KSTATE = ""
}
# catch the plex on the way through
$1 == "pl" { PL_CUR = $2
PL_TYPE = $7
PL_STATE = $5
PL_KSTATE = $4
# set an array if the volume is RAID5 & it has an
# enabled LOG plex
if ( FILENAME == POSTFAILURE && VOL_TYPE == "RAID" && PL_TYPE == "CONCAT" && PL_STATE == "LOG" && PL_KSTATE == "ENABLED" ) {
# set the array to be true
R5LOGOK[DG_CUR"~"VOL_CUR] = "true"
}
}
# record the subdisks found if they are valid
$1 == "sd" && $7 != "-" && $3 != "-" {
# work out the column & the offset
if ( index($7,"/") > 0 ) { COLUMN = substr($7,1,index($7,"/")-1) ; OFFSET = substr($7,index($7,"/")+1) } else { COLUMN = 0 ; OFFSET = $7 }
# store the data in the pre or post array
if ( FILENAME == PREFAILURE ) { PRESD[$2] = DG_CUR "~" VOL_CUR "~" $3 "~" PL_TYPE "~" $2 "~" $4 "~" $5 "~" $6 "~" COLUMN "~" OFFSET "~" PL_STATE "~" PL_KSTATE "~" $8 }
# store the data in the pre or post array
if ( FILENAME == POSTFAILURE ) { POSTSD[$2] = DG_CUR "~" VOL_CUR "~" $3 "~" PL_TYPE "~" $2 "~" $4 "~" $5 "~" $6 "~" COLUMN "~" OFFSET "~" PL_STATE "~" PL_KSTATE "~" $8 }
}
END {
# set some defaults
ITERATION=1
HSITERATION=1
# show what we are doing
print "\n" PROG ": scanning for disks affected by Hot Sparing" >"/dev/tty"
# check the DM info is the same between the PREFAILURE & POSTFAILURE files
# do the renames in this loop
# do the vxdisksetups in this loop
# do the vxdg adddisks in this loop
for ( DMNAME in ALLVXVMDISKS ) {
# create the DISKGROUP & DISKNAME variables - ease of use
DISKGROUP=substr(DMNAME,1,index(DMNAME,"~")-1)
DISKNAME=substr(DMNAME,index(DMNAME,"~")+1)
# define more usable variables
print "\nDMNAME = " DMNAME >DEBUG
CURRVM=POSTPHYSDISKS[POSTVXVMDISKS[DMNAME]]
print "CURRVM = " CURRVM >DEBUG
CURRPHYS=POSTVXVMDISKS[DMNAME]
print "CURRPHYS = " CURRPHYS >DEBUG
OLDVM=PREPHYSDISKS[POSTVXVMDISKS[DMNAME]]
print "OLDVM = " OLDVM >DEBUG
OLDPHYS=PREVXVMDISKS[DMNAME]
print "OLDPHYS = " OLDPHYS >DEBUG
# if the DG is not the requested one - continue to next record
if ( DISKGROUP !~ DGTOUSE ) { continue }
# see if a disk was in the old config but has disappeared from the
# current config
if ( CURRVM == "" && CURRPHYS == "" && OLDVM == "" && OLDPHYS != "" ) {
# informational message only
print PROG ": [GONE] " DMNAME " is no longer in VxVM cfg" >"/dev/tty"
}
# check if the disk now has the failing flag set & did not previously,
# if so turn it back off (also turn it of if the drive says NODEVICE as we
# do a vxreattach to hopefully fix this)
if ( DMINFOPRE[CURRVM] !~ /,FAILING$/ && ( DMINFOPOST[CURRVM] ~ /,FAILING$/ || DMINFOPOST[CURRVM] ~ /,NODEVICE$/ ) ) {
# set the spare the failing flag off
print PROG ": [FLAG] setting FAILING flag on " CURRVM " (" CURRPHYS ") \"off\"" >"/dev/tty"
# populate the HSFIX96 array fixes
HSFIX96[HSITERATION] = "/usr/sbin/vxedit -g " DISKGROUP " set failing=off " DISKNAME
}
# check to see if the VM disk name changed for this physical device
if ( CURRVM != OLDVM ) {
# check if the disk had the spare flag set previously,
# if so turn it back on
if ( DMINFOPRE[OLDVM] ~ /,SPARE$/ ) {
# set the spare flag back on
print PROG ": [FLAG] setting HS flag on " OLDVM " on " CURRPHYS " to \"on\"" >"/dev/tty"
# populate the HSFIX99 array - last run fixes
HSFIX99[HSITERATION] = "/usr/sbin/vxedit -g " DISKGROUP " set spare=on " substr(OLDVM,index(OLDVM,"~")+1)
}
# is this is a new disk that has appeared?
if ( OLDPHYS == "" ) {
# this disk has probably been added, no need to do anything here
print PROG ": [NEW] " DMNAME " on " CURRPHYS " is new to VxVM cfg" >"/dev/tty"
}
# determine whether this disk was renamed (as opposed to hotspared)
if ( OLDVM != "" && POSTVXVMDISKS[OLDVM] == "" && OLDPHYS == "" ) {
print PROG ": [REN] " OLDVM " has been renamed to " CURRVM >"/dev/tty"
print PROG ": [REN] renaming " CURRVM " to " OLDVM >"/dev/tty"
# populate the HSFIX90 array - first run fixes
HSFIX90[HSITERATION] = "/usr/sbin/vxedit -g " DISKGROUP " rename " DISKNAME " " substr(OLDVM,index(OLDVM,"~")+1)
}
}
# this disk has probably been involved in HotSparing
if ( CURRVM != OLDVM && CURRVM != "" && OLDVM != "" && OLDPHYS != "" && DMINFOPRE[OLDVM] ~ /SPARE/ ) {
# work out what it Hot Spared for
print PROG ": [HS] " OLDVM " has spared for " CURRVM " (" OLDPHYS ")" >"/dev/tty"
# first rename the hot spare back to what it was previously
print PROG ": [HS] renaming sparer " CURRVM " to " OLDVM >"/dev/tty"
# populate the fix arrays
HSFIX90[HSITERATION] = "/usr/sbin/vxedit -g " DISKGROUP " rename " DISKNAME " " HSTMP "." HSITERATION ".a"
HSFIX98[HSITERATION] = "/usr/sbin/vxedit -g " DISKGROUP " rename " HSTMP "." HSITERATION ".a " substr(OLDVM,index(OLDVM,"~")+1)
# if the OLDPHYS disk is back in the config, do a rename, if not
# do an initialise
print OLDPHYS >DEBUG
print POSTPHYSDISKS[OLDPHYS] >DEBUG
if ( POSTPHYSDISKS[OLDPHYS] == "" ) {
# initialise the disk
print PROG ": [HS] initialise & add disk " OLDPHYS " as " DISKNAME " to VxVM cfg" >"/dev/tty"
# get the private region length for this disk
split(DMINFOPRE[CURRVM],PRIVLENARRAY,",")
PRIVLEN=PRIVLENARRAY[4]
# populate the HSFIX91 array - near first run fixes
HSFIX91[HSITERATION] = "/etc/vx/bin/vxdisksetup -i " OLDPHYS " privlen=" PRIVLEN " ; /usr/sbin/vxdg -g " DISKGROUP " adddisk " substr(CURRVM,index(CURRVM,"~")+1) "=" OLDPHYS
} else {
# rename the disk
print PROG ": [HS] renaming spared " POSTPHYSDISKS[OLDPHYS] " to " CURRVM >"/dev/tty"
# populate the fix arrays
HSFIX91[HSITERATION] = "/usr/sbin/vxedit -g " DISKGROUP " rename " substr(POSTPHYSDISKS[OLDPHYS],index(POSTPHYSDISKS[OLDPHYS],"~")+1) " " HSTMP "." HSITERATION ".b"
HSFIX97[HSITERATION] = "/usr/sbin/vxedit -g " DISKGROUP " rename " HSTMP "." HSITERATION ".b " DISKNAME
}
}
# increment the HSITERATION counter
HSITERATION++
}
# start of HS fixes
print "\n# Start of HotSpare fixes\n"
# add all the HS fixes to the DOIT file
print "\n" PROG ": generating Host Sparing fixes" >"/dev/tty"
for ( FIX in HSFIX1 ) {
print "set -x ; sleep 5 ; " HSFIX1[FIX] " || { set +x ; shallicontinue ; set -x ; } "
}
for ( FIX in HSFIX2 ) {
print "set -x ; sleep 5 ; " HSFIX2[FIX] " || { set +x ; shallicontinue ; set -x ; } "
}
for ( FIX in HSFIX90 ) {
print "set -x ; sleep 5 ; " HSFIX90[FIX] " || { set +x ; shallicontinue ; set -x ; } "
}
for ( FIX in HSFIX91 ) {
print "set -x ; sleep 5 ; " HSFIX91[FIX] " || { set +x ; shallicontinue ; set -x ; } "
}
for ( FIX in HSFIX96 ) {
print "set -x ; sleep 5 ; " HSFIX96[FIX] " || { set +x ; shallicontinue ; set -x ; } "
}
for ( FIX in HSFIX97 ) {
print "set -x ; sleep 5 ; " HSFIX97[FIX] " || { set +x ; shallicontinue ; set -x ; } "
}
for ( FIX in HSFIX98 ) {
print "set -x ; sleep 5 ; " HSFIX98[FIX] " || { set +x ; shallicontinue ; set -x ; } "
}
for ( FIX in HSFIX99 ) {
print "set -x ; sleep 5 ; " HSFIX99[FIX] " || { set +x ; shallicontinue ; set -x ; } "
}
# end of HS fixes
print "\n# End of HotSpare fixes\n"
# start of RL fixes
print "\n# Start of Relocation fixes\n"
# on the first loop remember the disks that have been relocated, if we have to
# make a RAID5 log later, we will explicity exclude disks in this array
# we also use this to shorten/limit the next loop to only missing subdisks in
# the POSTFAILURE file
print "\n" PROG ": scanning for subdisks affected by Hot Relocation/Hot Sparing" >"/dev/tty"
for ( ELEMENT in PRESD ) {
# split the element into an array
split(PRESD[ELEMENT],T0,"~")
split(POSTSD[ELEMENT],T9,"~")
# get the subdisk name
SD_CHK = T0[5]
# if the subdisk is missing in the post file exclude it for use as R5log
# relocate target & populate an array to use in next loop for missing
# subdisks
if ( SD_CHK in POSTSD && T0[13] == T9[13] ) { system("true") } else {
# exclude this disk from being usedas a R5log
R5LOGEXCLUDE[T0[6]] = T0[6]
# populate the missing subdisks array
MISSINGSD[SD_CHK] = SD_CHK
# increment the counter
MISSINGSDCOUNT++
}
}
# give counts
for ( JUNK in R5LOGEXCLUDE ) {
AFFECTEDDISKCOUNT++
}
print PROG ": affected disk count = " AFFECTEDDISKCOUNT >"/dev/tty"
print PROG ": subdisks missing in Post.Failure = " MISSINGSDCOUNT >"/dev/tty"
# for each subdisk found build the fix file
print PROG ": building Hot Relocation fix file" >"/dev/tty"
for ( ELEMENT in MISSINGSD ) {
# set loop defaults
# split the element into an array
split(PRESD[ELEMENT],T0,"~")
split(POSTSD[ELEMENT],T9,"~")
# get the subdisk name
SD_CHK = T0[5]
# if the DG & VOL are not the requested ones - continue to next record
if ( T0[1] !~ DGTOUSE || T0[2] !~ VOLTOUSE ) { continue }
# see if it is in "post" & on the same physical device
if ( SD_CHK in POSTSD && T0[13] == T9[13] ) { system("true") } else { print PROG ": " T0[1] "/" T0[2] "/" T0[3] "/" SD_CHK " not correctly in Post.Failure!" >"/dev/tty"
# find any match subdisks in the "post" output
for ( T1 in POSTSD ) {
# split the element into an array
split(POSTSD[T1],T2,"~")
# check to see if the profile fits
#T0[5] != T2[5] && \
if ( \
T0[1] == T2[1] && \
T0[2] == T2[2] && \
T0[3] == T2[3] && \
T0[4] == T2[4] && \
T0[8] >= T2[8] && \
T0[9] == T2[9] && \
T0[10] = T2[10] + T2[8] ) { # this disk seems to have replaced the original
print PROG ": " T0[1] "/" T0[2] "/" T0[3] "/" T0[5] " replaced by " T2[5] >"/dev/tty"
#" column " T2[9] " offset " T2[10] " length " T2[8] >"/dev/tty"
# do the relocate commands if the subdisk is not on the same phyiscal
# disk
# create the target - unsplit subdisk
if ( T0[8] == T2[8] ) {
# the pre & post lengths are the same
print "sleep 5 ; /usr/sbin/vxmake -g " T0[1] " sd VxSunSD-" ITERATION " len=" T2[8] " offset=" T0[7] " " T0[6] " || { set +x ; shallicontinue ; set -x ; }"
}
# create the target - split subdisk
if ( T0[8] != T2[8] ) {
# adjust the offset as the subdisk has been split
print "sleep 5 ; /usr/sbin/vxmake -g " T0[1] " sd VxSunSD-" ITERATION " len=" T2[8] " offset=" T0[7] + T2[10] - T0[10] " " T0[6] " || { set +x ; shallicontinue ; set -x ; }"
}
# move the impostor to the target
# check to see if this is a RAID5 data/parity subdisk
if ( T2[4] == "RAID" ) {
# it is a RAID5 subdisk - check to see if it has a valid
# R5 log attached
if ( R5LOGOK[T0[1]"~"T0[2]] == "true" ) {
# there is a log attached
print "sleep 5 ; /usr/sbin/vxsd -o rm -g " T0[1] " mv " T2[5] " VxSunSD-" ITERATION " || { set +x ; shallicontinue ; set -x ; }"
} else {
# there is not a log attached - attempt to
# attach one excluding affected disks
print "sleep 5"
printf("/usr/sbin/vxassist -g %s addlog %s",T0[1],T0[2])
# for each excluded disk
for ( XD in R5LOGEXCLUDE ) {
printf(" !%s ",XD)
}
# record the exit value of vxassist
print "\nADDLOGEXIT=\"\$\?\""
# check to see if the addlog succeeded
print "set +x"
print "if [ \"\${ADDLOGEXIT}\" = \"0\" ]"
print "then echo \"\\n\${PROG}: a RAID5 log for volume " T0[2] " was attached for data protection\""
print " echo \"\${PROG}: the RAID5 log will not be removed automatically\""
print " echo \"\${PROG}: it is recommended that the RAID5 log remain in place\""
print " echo \"\${PROG}: the RAID5 log may be removed manually after completion\\n\""
print " set -x ; sleep 5 ; /usr/sbin/vxsd -o rm -g " T0[1] " mv " T2[5] " VxSunSD-" ITERATION " || { set +x ; shallicontinue ; set -x ; }"
print ""
print "else # prompt the use to verify the move as it is considered dangerous"
print " echo \"\\n\${PROG}: unable to attach a RAID5 log for volume " T0[2] "!\""
print " echo \"\\n\\007\${PROG}: About to move a subdisk on a RAID5 volume without a RAID5 log\""
print " echo \"\${PROG}: Please confirm you wish to do this (y/n): \\c\""
print " read OKTOMOVE"
print ""
print " if [ \"\${OKTOMOVE}\" = \"Y\" -o \"\${OKTOMOVE}\" = \"y\" ] "
print " then # do it"
print " echo \"\""
print " set -x ; sleep 5 "
print " /usr/sbin/vxsd -f -o rm -g " T0[1] " mv " T2[5] " VxSunSD-" ITERATION " || { set +x ; shallicontinue ; set -x ; }"
print " set +x "
print ""
print " else # give a message"
print " echo \"\${PROG}: " T2[5] " will not be moved!\\n\""
print " fi"
print "fi"
print "set -x"
}
} else {
# it is an ordinary subdisk
print "sleep 5 ; /usr/sbin/vxsd -o rm -g " T0[1] " mv " T2[5] " VxSunSD-" ITERATION " || { set +x ; shallicontinue ; set -x ; }"
}
# add this to the array for the subdisk joins
JOIN[T0[5]] = JOIN[T0[5]] T2[10]",VxSunSD-" ITERATION "~"
DG[T0[5]] = T0[1]
# increment the counter
ITERATION++
}
}
}
# see if it is in "post" - RAID5 log subdisks
if ( T0[11] == "LOG" ) {
if ( SD_CHK in POSTSD ) { system("true") } else { print PROG ": " T0[1] "/" T0[2] "/" T0[3] "/" SD_CHK " RAID5 log not correctly in Post.Failure!" >"/dev/tty"
# find any match subdisks in the "post" output
for ( T1 in POSTSD ) {
# split the element into an array
split(POSTSD[T1],T2,"~")
# if the log disk found here existed beforehand we
# have probably found a valid mirrored R5 log
if ( T2[5] in PRESD ) { continue }
# check to see if the profile fits
if ( T0[5] != T2[5] && \
T0[1] == T2[1] && \
T0[2] == T2[2] && \
T0[11] == T2[11] && \
T0[4] == T2[4] && \
T0[8] >= T2[8] && \
T0[9] == T2[9] && \
T0[10] = T2[10] + T2[8] ) { # this disk seems to have replaced the original
print PROG ": " T0[1] "/" T0[2] "/" T0[3] "/" T0[5] " RAID5 log replaced by " T2[5] >"/dev/tty"
#" column " T2[9] " offset " T2[10] " length " T2[8] >"/dev/tty"
# do the relocate commands
# create the target
# the pre & post lengths do not matter here
print "sleep 5 ; /usr/sbin/vxmake -g " T0[1] " sd VXsunR5-" ITERATION " len=" T2[8] " offset=" T0[7] " " T0[6] " || { set +x ; shallicontinue ; set -x ; }"
# create the original R5LOG plex
print "sleep 5 ; /usr/sbin/vxmake -g " T0[1] " plex " T0[3] " sd=VXsunR5-" ITERATION " || { set +x ; shallicontinue ; set -x ; }"
# attach the original R5LOG plex
print "sleep 5 ; /usr/sbin/vxplex -g " T0[1] " att " T0[2] " " T0[3]
# remove the replacement R5LOG plex
print "sleep 5 ; /usr/sbin/vxplex -g " T0[1] " dis " T2[3]
# remove the impostor
print "sleep 5 ; /usr/sbin/vxedit -g " T0[1] " -r rm " T2[3] " || { set +x ; shallicontinue ; set -x ; } "
# rename the replacement subdisk
print "sleep 5 ; /usr/sbin/vxedit -g " T0[1] " rename VXsunR5-" ITERATION " " T0[5] " || { set +x ; shallicontinue ; set -x ; } "
}
}
}
}
}
# for each JOIN
for ( ELEMENT in JOIN ) {
# get the disk group to use
DG_CUR = DG[ELEMENT]
# split the ELEMENT into an array
ELEMENT_COUNT = split(JOIN[ELEMENT],T3,"~")
# for each subdisk
if ( ELEMENT_COUNT == 2 ) { print "sleep 5 ; /usr/sbin/vxedit -g " DG_CUR " rename " substr(T3[1],index(T3[1],",")+1) " " ELEMENT " || { set +x ; shallicontinue ; set -x ; } " } else {
# for each element add to the join
for ( T4 in T3 ) {
# if the record is not blank
if ( T3[T4] !~ /^[ ]*$/ ) {
printf(" %s \\\n",T3[T4]) >SORTTMP
}
}
# close the file
close(SORTTMP)
# sort the file by offset number
system("/usr/bin/sort -n -o " SORTTMP " " SORTTMP)
# start the command
printf("sleep 5 ; /usr/sbin/vxsd -g " DG_CUR " join ")
# cat the sort file
system("/bin/cut -f2 -d, " SORTTMP)
# close off the command
printf(" %s || { set +x ; shallicontinue ; set -x ; }\n",ELEMENT)
}
}
# End of RL fixes
print "\n# End of Relocation fixes\n"
} ' ${PREFAILURE} ${POSTFAILURE}
# close off the doit file
cat ${NOW}
# copy & sort the PREFAILURE layout
/usr/bin/sort ${PREFAILURE} >${SANITYTMP}
# give a warning that there may be variations if ...
cat START"
/bin/diff ${SANITYTMP} ${NOW}
echo "*** Differences in Pre.Failure & Post.Failure configuration => END"
# remove the temp file
rm -f ${NOW} ${SANITYTMP}
else # show we can not sanity check
echo "\n\${PROG}: unable to sanity check fixed configuration"
fi
# show finish date
echo "\n\${PROG}: finished @ \`date\` \n"
EOF_SANITY
) >${DOIT}
# explain that the file has been created
echo "\n${PROG}: reconfiguration script created in \"${DOIT}\" ..."
chmod 700 ${DOIT}
# remove the temp sort file
rm -f ${SORTTMP} ${LOCALVXPRINT}
# ask user whether DOIT should be run now
echo "\n${PROG}: Do you wish to run \"${DOIT}\" now? \c"
read RUNDOIT
case "${RUNDOIT}" in
y|Y) # run the newly created DOIT file
echo "\n${PROG}: running reconfiguration script \"${DOIT}\" ... \n"
${DOIT}
;;
*) # run the newly created DOIT file
echo "\n${PROG}: not running reconfiguration script \"${DOIT}\" ... \n"
;;
esac
本文来自ChinaUnix博客,如果查看原文请点:http://blog.chinaunix.net/u/43/showart_100120.html |
|