From 3304fb0e1f1eeb2bfe52611541c5dd12bdc908e0 Mon Sep 17 00:00:00 2001 From: Scott Little Date: Mon, 2 Oct 2017 15:12:54 -0400 Subject: [PATCH 06/13] WRS: Patch1110: lvm_vg_activation.patch --- heartbeat/LVM | 130 +++++++++++++++++++++++++++++++++++++++++++++++++++------- 1 file changed, 116 insertions(+), 14 deletions(-) diff --git a/heartbeat/LVM b/heartbeat/LVM index 5de88b6..3a52e56 100755 --- a/heartbeat/LVM +++ b/heartbeat/LVM @@ -449,6 +449,81 @@ retry_exclusive_start() } # +# Activate one volume explicitly. +# +activate_volume() { + ocf_run lvchange $1 /dev/${2}/$3 + if [ $? -eq 0 ] ; then + ocf_log info "Succesfully activated $LV." + else + ocf_log err "Problem activating $LV." + fi +} + +# +# Kick off parallel activation of all volumes +# +activate_all_volumes() { + VG=$1 + shift + lvchange_args="$*" + + # Get the list of volumes, without the first line which is column headings. + VOLS=`lvs $VG |tail -n +2` + + while read -r LINE; do + # Convert the line into an array. + LINE_ARRAY=($LINE) + + # First array element is the volume/snapshot name. + LV=${LINE_ARRAY[0]} + + # Third array element is the attributes. + ATTR=${LINE_ARRAY[2]} + + # Fifth character in the attributes is "a" if it's active. + ACTIVE=${ATTR:4:1} + if [ "$ACTIVE" == "a" ]; then + ocf_log info "$LV is already active." + continue + fi + + SNAPSHOT_ORIGIN=${LINE_ARRAY[4]} + if [ "$SNAPSHOT_ORIGIN" != "" ] ; then + # If this is a snapshot, don't activate it. + continue + fi + + ( activate_volume "$*" $VG $LV ) & + done <<< "$VOLS" +} + +# +# Scan for inactive volumes and log any that are found. +# +log_inactive_volumes() { + # Get the list of volumes, without the first line which is column headings. + VOLS=`lvs $1 |tail -n +2` + + while read -r LINE; do + # Convert the line into an array. + LINE_ARRAY=($LINE) + + # First array element is the volume/snapshot name. + LV=${LINE_ARRAY[0]} + + # Third array element is the attributes. + ATTR=${LINE_ARRAY[2]} + + # Fifth character in the attributes is "a" if it's active. + ACTIVE=${ATTR:4:1} + if [ "$ACTIVE" != "a" ]; then + ocf_log err "Volume $LV is not active after expiry of timeout." + fi + done <<< "$VOLS" +} + +# # Enable LVM volume # LVM_start() { @@ -489,20 +564,47 @@ EOF : ;; esac - if ! ocf_run vgchange $vgchange_options $vg; then - if [ $clvmd -eq 0 ]; then - return $OCF_ERR_GENERIC - fi - - # Failure to exclusively activate cluster vg.: - # This could be caused by a remotely active LV, Attempt - # to disable volume group cluster wide and try again. - # Allow for some settling - sleep 5 - if ! retry_exclusive_start; then - return $OCF_ERR_GENERIC - fi - fi + # Kick off activation of all volumes. If it doesn't complete within + # the timeout period, then we'll log the not-yet-activated volumes and + # continue on. + (ocf_run vgchange $vgchange_options $1) & PID=$! + + # Check every second for up to TIMEOUT seconds whether the vgchange has + # completed. + TIMEOUT=300 + TIMED_OUT=true + SECONDS=0; + PARALLEL_ACTIVATE_DELAY=10 + PARALLEL_ACTIVATE_DONE=false + while [ $SECONDS -lt $TIMEOUT ] ; do + kill -0 $PID &> /dev/null + if [ $? -eq 1 ] ; then + # process with pid of $PID doesn't exist, vgchange command completed + TIMED_OUT=false + break + fi + if [ $SECONDS -ge $PARALLEL_ACTIVATE_DELAY ] && \ + [ "$PARALLEL_ACTIVATE_DONE" != true ] && \ + [ "$1" == "cinder-volumes" ] ; then + # This will kick off parallel activation of all LVs in the VG. + # The delay is to ensure the VG is activated first. + PARALLEL_ACTIVATE_DONE=true + ocf_log info Explicitly activating all volumes in $1 with: $vgchange_options + activate_all_volumes $1 $vgchange_options + fi + sleep 1 + done + + if [ "$TIMED_OUT" = true ] ; then + ocf_log err "Timed out running ocf_run vgchange $vgchange_options $1" + log_inactive_volumes $1 + else + # Child process completed, get its status. + wait $PID + if [ $? -ne 0 ] ; then + return $OCF_ERR_GENERIC + fi + fi if LVM_status $vg; then : OK Volume $vg activated just fine! -- 1.9.1