]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - tests/zfs-tests/tests/functional/cli_root/zpool_import/import_rewind_config_changed.ksh
Remove races from scrub / resilver tests
[FreeBSD/FreeBSD.git] / tests / zfs-tests / tests / functional / cli_root / zpool_import / import_rewind_config_changed.ksh
1 #!/bin/ksh -p
2
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
14 #
15 # Copyright (c) 2017 by Delphix. All rights reserved.
16 #
17
18 . $STF_SUITE/tests/functional/cli_root/zpool_import/zpool_import.kshlib
19
20 #
21 # DESCRIPTION:
22 #       It should be possible to rewind a pool beyond a configuration change.
23 #
24 # STRATEGY:
25 #       1. Create a pool.
26 #       2. Generate files and remember their md5sum.
27 #       3. Note last synced txg.
28 #       4. Take a snapshot to make sure old blocks are not overwritten.
29 #       5. Perform zpool add/attach/detach/remove operation.
30 #       6. Change device paths if requested and re-import pool.
31 #       7. Checkpoint the pool as one last attempt to preserve old blocks.
32 #       8. Overwrite the files.
33 #       9. Export the pool.
34 #       10. Verify that we can rewind the pool to the noted txg.
35 #       11. Verify that the files are readable and retain their old data.
36 #
37 # DISCLAIMER:
38 #       This test can fail since nothing guarantees that old MOS blocks aren't
39 #       overwritten. Snapshots protect datasets and data files but not the MOS.
40 #       sync_some_data_a_few_times interleaves file data and MOS data for a few
41 #       txgs, thus increasing the odds that some txgs will have their MOS data
42 #       left untouched.
43 #
44
45 verify_runnable "global"
46
47 function custom_cleanup
48 {
49         set_vdev_validate_skip 0
50         cleanup
51         log_must set_tunable64 vdev_min_ms_count 16
52 }
53
54 log_onexit custom_cleanup
55
56 function test_common
57 {
58         typeset poolcreate="$1"
59         typeset addvdevs="$2"
60         typeset attachargs="${3:-}"
61         typeset detachvdev="${4:-}"
62         typeset removevdev="${5:-}"
63         typeset finalpool="${6:-}"
64
65         typeset poolcheck="$poolcreate"
66
67         log_must zpool create $TESTPOOL1 $poolcreate
68
69         log_must generate_data $TESTPOOL1 $MD5FILE
70
71         # syncing a few times while writing new data increases the odds that MOS
72         # metadata for some of the txgs will survive
73         log_must sync_some_data_a_few_times $TESTPOOL1
74         typeset txg
75         txg=$(get_last_txg_synced $TESTPOOL1)
76         log_must zfs snapshot -r $TESTPOOL1@snap1
77
78         #
79         # Perform config change operations
80         #
81         if [[ -n $addvdevs ]]; then
82                 log_must zpool add -f $TESTPOOL1 $addvdevs
83         fi
84         if [[ -n $attachargs ]]; then
85                 log_must zpool attach $TESTPOOL1 $attachargs
86         fi
87         if [[ -n $detachvdev ]]; then
88                 log_must zpool detach $TESTPOOL1 $detachvdev
89         fi
90         if [[ -n $removevdev ]]; then
91                 [[ -z $finalpool ]] &&
92                     log_fail "Must provide final pool status!"
93                 log_must zpool remove $TESTPOOL1 $removevdev
94                 log_must wait_for_pool_config $TESTPOOL1 "$finalpool"
95         fi
96         if [[ -n $pathstochange ]]; then
97                 #
98                 # Change device paths and re-import pool to update labels
99                 #
100                 zpool export $TESTPOOL1
101                 for dev in $pathstochange; do
102                         log_must mv $dev "${dev}_new"
103                         poolcheck=$(echo "$poolcheck" | \
104                             sed "s:$dev:${dev}_new:g")
105                 done
106                 zpool import -d $DEVICE_DIR $TESTPOOL1
107         fi
108
109         #
110         # In an attempt to leave MOS data untouched so extreme
111         # rewind is successful during import we checkpoint the
112         # pool and hope that these MOS data are part of the
113         # checkpoint (e.g they stay around). If this goes as
114         # expected, then extreme rewind should rewind back even
115         # further than the time that we took the checkpoint.
116         #
117         # Note that, ideally we would want to take a checkpoint
118         # right after we recond the txg we plan to rewind to.
119         # But since we can't attach, detach or remove devices
120         # while having a checkpoint, we take it after the
121         # operation that changes the config.
122         #
123         log_must zpool checkpoint $TESTPOOL1
124
125         log_must overwrite_data $TESTPOOL1 ""
126
127         log_must zpool export $TESTPOOL1
128
129         log_must zpool import -d $DEVICE_DIR -T $txg $TESTPOOL1
130         log_must check_pool_config $TESTPOOL1 "$poolcheck"
131
132         log_must verify_data_md5sums $MD5FILE
133
134         # Cleanup
135         log_must zpool destroy $TESTPOOL1
136         if [[ -n $pathstochange ]]; then
137                 for dev in $pathstochange; do
138                         log_must mv "${dev}_new" $dev
139                 done
140         fi
141         # Fast way to clear vdev labels
142         log_must zpool create -f $TESTPOOL2 $VDEV0 $VDEV1 $VDEV2 $VDEV3 $VDEV4
143         log_must zpool destroy $TESTPOOL2
144
145         log_note ""
146 }
147
148 function test_add_vdevs
149 {
150         typeset poolcreate="$1"
151         typeset addvdevs="$2"
152
153         log_note "$0: pool '$poolcreate', add $addvdevs."
154
155         test_common "$poolcreate" "$addvdevs"
156 }
157
158 function test_attach_vdev
159 {
160         typeset poolcreate="$1"
161         typeset attachto="$2"
162         typeset attachvdev="$3"
163
164         log_note "$0: pool '$poolcreate', attach $attachvdev to $attachto."
165
166         test_common "$poolcreate" "" "$attachto $attachvdev"
167 }
168
169 function test_detach_vdev
170 {
171         typeset poolcreate="$1"
172         typeset detachvdev="$2"
173
174         log_note "$0: pool '$poolcreate', detach $detachvdev."
175
176         test_common "$poolcreate" "" "" "$detachvdev"
177 }
178
179 function test_attach_detach_vdev
180 {
181         typeset poolcreate="$1"
182         typeset attachto="$2"
183         typeset attachvdev="$3"
184         typeset detachvdev="$4"
185
186         log_note "$0: pool '$poolcreate', attach $attachvdev to $attachto," \
187             "then detach $detachvdev."
188
189         test_common "$poolcreate" "" "$attachto $attachvdev" "$detachvdev"
190 }
191
192 function test_remove_vdev
193 {
194         typeset poolcreate="$1"
195         typeset removevdev="$2"
196         typeset finalpool="$3"
197
198         log_note "$0: pool '$poolcreate', remove $removevdev."
199
200         test_common "$poolcreate" "" "" "" "$removevdev" "$finalpool"
201 }
202
203 # Record txg history
204 is_linux && log_must set_tunable32 zfs_txg_history 100
205
206 # Make the devices bigger to reduce chances of overwriting MOS metadata.
207 increase_device_sizes $(( FILE_SIZE * 4 ))
208
209 # Increase the number of metaslabs for small pools temporarily to
210 # reduce the chance of reusing a metaslab that holds old MOS metadata.
211 log_must set_tunable64 vdev_min_ms_count 150
212
213 # Part of the rewind test is to see how it reacts to path changes
214 typeset pathstochange="$VDEV0 $VDEV1 $VDEV2 $VDEV3"
215
216 log_note " == test rewind after device addition == "
217
218 test_add_vdevs "$VDEV0" "$VDEV1"
219 test_add_vdevs "$VDEV0 $VDEV1" "$VDEV2"
220 test_add_vdevs "$VDEV0" "$VDEV1 $VDEV2"
221 test_add_vdevs "mirror $VDEV0 $VDEV1" "mirror $VDEV2 $VDEV3"
222 test_add_vdevs "$VDEV0" "raidz $VDEV1 $VDEV2 $VDEV3"
223 test_add_vdevs "$VDEV0" "log $VDEV1"
224 test_add_vdevs "$VDEV0 log $VDEV1" "$VDEV2"
225
226 log_note " == test rewind after device attach == "
227
228 test_attach_vdev "$VDEV0" "$VDEV0" "$VDEV1"
229 test_attach_vdev "mirror $VDEV0 $VDEV1" "$VDEV0" "$VDEV2"
230 test_attach_vdev "$VDEV0 $VDEV1" "$VDEV0" "$VDEV2"
231
232 log_note " == test rewind after device removal == "
233
234 # Once we remove a device it will be overlooked in the device scan, so we must
235 # preserve its original path
236 pathstochange="$VDEV0 $VDEV2"
237 test_remove_vdev "$VDEV0 $VDEV1 $VDEV2" "$VDEV1" "$VDEV0 $VDEV2"
238
239 #
240 # Path change and detach are incompatible. Detach changes the guid of the vdev
241 # so we have no direct way to link the new path to an existing vdev.
242 #
243 pathstochange=""
244
245 log_note " == test rewind after device detach == "
246
247 test_detach_vdev "mirror $VDEV0 $VDEV1" "$VDEV1"
248 test_detach_vdev "mirror $VDEV0 $VDEV1 mirror $VDEV2 $VDEV3" "$VDEV1"
249 test_detach_vdev "$VDEV0 log mirror $VDEV1 $VDEV2" "$VDEV2"
250
251 log_note " == test rewind after device attach followed by device detach == "
252
253 #
254 # We need to disable vdev validation since once we detach VDEV1, VDEV0 will
255 # inherit the mirror tvd's guid and lose its original guid.
256 #
257 set_vdev_validate_skip 1
258 test_attach_detach_vdev "$VDEV0" "$VDEV0" "$VDEV1" "$VDEV1"
259 set_vdev_validate_skip 0
260
261 log_pass "zpool import rewind after configuration change passed."