1# 2# CDDL HEADER START 3# 4# This file and its contents are supplied under the terms of the 5# Common Development and Distribution License ("CDDL"), version 1.0. 6# You may only use this file in accordance with the terms of version 7# 1.0 of the CDDL. 8# 9# A full copy of the text of the CDDL should have accompanied this 10# source. A copy of the CDDL is also available via the Internet at 11# http://www.illumos.org/license/CDDL. 12# 13# CDDL HEADER END 14# 15 16# 17# Copyright (c) 2014, 2016 by Delphix. All rights reserved. 18# 19 20export REMOVEDISK=${DISKS%% *} 21export NOTREMOVEDISK=${DISKS##* } 22 23# 24# Waits for the pool to finish a removal. If an optional callback is given, 25# execute it every 0.5s. 26# 27# Example usage: 28# 29# wait_for_removal $TESTPOOL dd if=/dev/urandom of=/$TESTPOOL/file count=1 30# 31function wait_for_removal # pool [callback args] 32{ 33 typeset pool=$1 34 typeset callback=$2 35 36 [[ -n $callback ]] && shift 2 37 38 while is_pool_removing $pool; do 39 [[ -z $callback ]] || log_must $callback "$@" 40 sleep 0.5 41 done 42 43 # 44 # The pool state changes before the TXG finishes syncing; wait for 45 # the removal to be completed on disk. 46 # 47 sync 48 49 log_must is_pool_removed $pool 50 return 0 51} 52 53function indirect_vdev_mapping_size # pool 54{ 55 typeset pool=$1 56 zdb -P $pool | grep 'indirect vdev' | \ 57 sed -E 's/.*\(([0-9]+) in memory\).*/\1/g' 58} 59 60function random_write # file write_size 61{ 62 typeset file=$1 63 typeset block_size=$2 64 typeset file_size=$(stat -c%s $file 2>/dev/null) 65 typeset nblocks=$((file_size / block_size)) 66 67 [[ -w $file ]] || return 1 68 69 dd if=/dev/urandom of=$file conv=notrunc \ 70 bs=$block_size count=1 seek=$((RANDOM % nblocks)) >/dev/null 2>&1 71} 72 73_test_removal_with_operation_count=0 74function _test_removal_with_operation_cb # real_callback 75{ 76 typeset real_callback=$1 77 78 $real_callback $_test_removal_with_operation_count || \ 79 log_fail $real_callback "failed after" \ 80 $_test_removal_with_operation_count "iterations" 81 82 (( _test_removal_with_operation_count++ )) 83 84 log_note "Callback called $((_test_removal_with_operation_count)) times" 85 86 return 0 87} 88 89function start_random_writer # file 90{ 91 typeset file=$1 92 ( 93 log_note "Starting writer for $file" 94 # This will fail when we destroy the pool. 95 while random_write $file $((2**12)); do 96 : 97 done 98 log_note "Stopping writer for $file" 99 ) & 100} 101 102function set_min_bytes # bytes 103{ 104 typeset bytes=$1 105 echo "zfs_condense_min_mapping_bytes/W 0t$bytes" | \ 106 mdb -kw 107} 108 109# 110# The callback should be a function that takes as input the number of 111# iterations and the given arguments. 112# 113function test_removal_with_operation # callback [count] 114{ 115 typeset operation=$1 116 typeset count=$2 117 118 [[ -n $count ]] || count=0 119 120 # 121 # To ensure that the removal takes a while, we fragment the pool 122 # by writing random blocks and continue to do during the removal. 123 # 124 log_must mkfile 1g $TESTDIR/$TESTFILE0 125 for i in $(seq $((2**10))); do 126 random_write $TESTDIR/$TESTFILE0 $((2**12)) || \ 127 log_fail "Could not write to $TESTDIR/$TESTFILE0." 128 done 129 start_random_writer $TESTDIR/$TESTFILE0 1g 130 killpid=$! 131 132 log_must zpool remove $TESTPOOL $REMOVEDISK 133 log_must wait_for_removal $TESTPOOL \ 134 _test_removal_with_operation_cb $operation 135 log_mustnot vdevs_in_pool $TESTPOOL $REMOVEDISK 136 log_must zdb -cd $TESTPOOL 137 138 kill $killpid 139 wait 140 141 # 142 # We would love to assert that the callback happened *during* the 143 # removal, but we don't have the ability to be confident of that 144 # (via limiting bandwidth, etc.) yet. Instead, we try again. 145 # 146 if (( $_test_removal_with_operation_count <= 1 )); then 147 (( count <= 5 )) || log_fail "Attempted test too many times." 148 149 log_note "Callback only called" \ 150 $_test_removal_with_operation_count \ 151 "times, trying again." 152 default_setup_noexit "$DISKS" 153 test_removal_with_operation $operation $((count + 1)) 154 fi 155} 156