Whamcloud - gitweb
LU-12624 lod: alloc dir stripes by QoS
[fs/lustre-release.git] / lustre / tests / sanity.sh
1 #!/bin/bash
2 #
3 # Run select tests by setting ONLY, or as arguments to the script.
4 # Skip specific tests by setting EXCEPT.
5 #
6 # e.g. ONLY="22 23" or ONLY="`seq 32 39`" or EXCEPT="31"
7 set -e
8
9 ONLY=${ONLY:-"$*"}
10
11 # Check Grants after these tests
12 GRANT_CHECK_LIST="$GRANT_CHECK_LIST 42a 42b 42c 42d 42e 63a 63b 64a 64b 64c 64d"
13
14 OSC=${OSC:-"osc"}
15
16 CC=${CC:-cc}
17 CREATETEST=${CREATETEST:-createtest}
18 LVERIFY=${LVERIFY:-ll_dirstripe_verify}
19 OPENFILE=${OPENFILE:-openfile}
20 OPENUNLINK=${OPENUNLINK:-openunlink}
21 READS=${READS:-"reads"}
22 MUNLINK=${MUNLINK:-munlink}
23 SOCKETSERVER=${SOCKETSERVER:-socketserver}
24 SOCKETCLIENT=${SOCKETCLIENT:-socketclient}
25 MEMHOG=${MEMHOG:-memhog}
26 DIRECTIO=${DIRECTIO:-directio}
27 ACCEPTOR_PORT=${ACCEPTOR_PORT:-988}
28 DEF_STRIPE_COUNT=-1
29 CHECK_GRANT=${CHECK_GRANT:-"yes"}
30 GRANT_CHECK_LIST=${GRANT_CHECK_LIST:-""}
31 export PARALLEL=${PARALLEL:-"no"}
32
33 TRACE=${TRACE:-""}
34 LUSTRE_TESTS_API_DIR=${LUSTRE_TESTS_API_DIR:-${LUSTRE}/tests/clientapi}
35 LUSTRE=${LUSTRE:-$(dirname $0)/..}
36 . $LUSTRE/tests/test-framework.sh
37 init_test_env $@
38
39 init_logging
40
41 ALWAYS_EXCEPT="$SANITY_EXCEPT "
42 # bug number for skipped test: LU-9693 LU-6493 LU-9693
43 ALWAYS_EXCEPT+="               42a     42b     42c "
44 # bug number:    LU-8411 LU-9054
45 ALWAYS_EXCEPT+=" 407     312 "
46
47 if $SHARED_KEY; then
48         # bug number:    LU-9795 LU-9795 LU-9795 LU-9795
49         ALWAYS_EXCEPT+=" 17n     60a     133g    300f "
50 fi
51
52 # skip the grant tests for ARM until they are fixed
53 if [[ $(uname -m) = aarch64 ]]; then
54         # bug number:    LU-11596
55         ALWAYS_EXCEPT+=" $GRANT_CHECK_LIST"
56         # bug number:    LU-11671 LU-11667 LU-4398
57         ALWAYS_EXCEPT+=" 45       317      817"
58 fi
59
60 #                                  5          12          (min)"
61 [ "$SLOW" = "no" ] && EXCEPT_SLOW="27m 64b 68 71 115 300o"
62
63 if [ "$mds1_FSTYPE" = "zfs" ]; then
64         # bug number for skipped test:
65         ALWAYS_EXCEPT="$ALWAYS_EXCEPT  "
66         #                                               13    (min)"
67         [ "$SLOW" = "no" ] && EXCEPT_SLOW="$EXCEPT_SLOW 51b"
68 fi
69
70 # Get the SLES distro version
71 #
72 # Returns a version string that should only be used in comparing
73 # strings returned by version_code()
74 sles_version_code()
75 {
76         local version=$(grep VERSION_ID /etc/os-release | cut -d'"' -f2)
77
78         # All SuSE Linux versions have one decimal. version_code expects two
79         local sles_version=$version.0
80         version_code $sles_version
81 }
82
83 # Check if we are running on Ubuntu or SLES so we can make decisions on
84 # what tests to run
85 if [ -r /etc/SuSE-release ]; then
86         sles_version=$(sles_version_code)
87         [ $sles_version -lt $(version_code 11.4.0) ] &&
88                 # bug number for skipped test: LU-4341
89                 ALWAYS_EXCEPT="$ALWAYS_EXCEPT  170"
90         [ $sles_version -lt $(version_code 12.0.0) ] &&
91                 # bug number for skipped test: LU-3703
92                 ALWAYS_EXCEPT="$ALWAYS_EXCEPT  234"
93 elif [ -r /etc/os-release ]; then
94         if grep -qi ubuntu /etc/os-release; then
95                 ubuntu_version=$(version_code $(sed -n -e 's/"//g' \
96                                                 -e 's/^VERSION=//p' \
97                                                 /etc/os-release |
98                                                 awk '{ print $1 }'))
99
100                 if [[ $ubuntu_version -gt $(version_code 16.0.0) ]]; then
101                         # bug number for skipped test:
102                         #                LU-10334 LU-10366
103                         ALWAYS_EXCEPT+=" 103a     410"
104                 fi
105         fi
106 fi
107
108 build_test_filter
109 FAIL_ON_ERROR=false
110
111 cleanup() {
112         echo -n "cln.."
113         pgrep ll_sa > /dev/null && { echo "There are ll_sa thread not exit!"; exit 20; }
114         cleanupall ${FORCE} $* || { echo "FAILed to clean up"; exit 20; }
115 }
116 setup() {
117         echo -n "mnt.."
118         load_modules
119         setupall || exit 10
120         echo "done"
121 }
122
123 check_swap_layouts_support()
124 {
125         $LCTL get_param -n llite.*.sbi_flags | grep -q layout ||
126                 skip "Does not support layout lock."
127 }
128
129 check_and_setup_lustre
130 DIR=${DIR:-$MOUNT}
131 assert_DIR
132
133 MAXFREE=${MAXFREE:-$((200000 * $OSTCOUNT))}
134
135 [ -f $DIR/d52a/foo ] && chattr -a $DIR/d52a/foo
136 [ -f $DIR/d52b/foo ] && chattr -i $DIR/d52b/foo
137 rm -rf $DIR/[Rdfs][0-9]*
138
139 # $RUNAS_ID may get set incorrectly somewhere else
140 [ $UID -eq 0 -a $RUNAS_ID -eq 0 ] &&
141         error "\$RUNAS_ID set to 0, but \$UID is also 0!"
142
143 check_runas_id $RUNAS_ID $RUNAS_GID $RUNAS
144
145 if [ "${ONLY}" = "MOUNT" ] ; then
146         echo "Lustre is up, please go on"
147         exit
148 fi
149
150 echo "preparing for tests involving mounts"
151 EXT2_DEV=${EXT2_DEV:-$TMP/SANITY.LOOP}
152 touch $EXT2_DEV
153 mke2fs -j -F $EXT2_DEV 8000 > /dev/null
154 echo # add a newline after mke2fs.
155
156 umask 077
157
158 OLDDEBUG=$(lctl get_param -n debug 2> /dev/null)
159 lctl set_param debug=-1 2> /dev/null || true
160 test_0a() {
161         touch $DIR/$tfile
162         $CHECKSTAT -t file $DIR/$tfile || error "$tfile is not a file"
163         rm $DIR/$tfile
164         $CHECKSTAT -a $DIR/$tfile || error "$tfile was not removed"
165 }
166 run_test 0a "touch; rm ====================="
167
168 test_0b() {
169         chmod 0755 $DIR || error "chmod 0755 $DIR failed"
170         $CHECKSTAT -p 0755 $DIR || error "$DIR permission is not 0755"
171 }
172 run_test 0b "chmod 0755 $DIR ============================="
173
174 test_0c() {
175         $LCTL get_param mdc.*.import | grep "state: FULL" ||
176                 error "import not FULL"
177         $LCTL get_param mdc.*.import | grep "target: $FSNAME-MDT" ||
178                 error "bad target"
179 }
180 run_test 0c "check import proc"
181
182 test_0d() { # LU-3397
183         [ $MGS_VERSION -lt $(version_code 2.10.57) ] &&
184                 skip "proc exports not supported before 2.10.57"
185
186         local mgs_exp="mgs.MGS.exports"
187         local client_uuid=$($LCTL get_param -n mgc.*.uuid)
188         local exp_client_nid
189         local exp_client_version
190         local exp_val
191         local imp_val
192         local temp_imp=$DIR/$tfile.import
193         local temp_exp=$DIR/$tfile.export
194
195         # save mgc import file to $temp_imp
196         $LCTL get_param mgc.*.import | tee $temp_imp
197         # Check if client uuid is found in MGS export
198         for exp_client_nid in $(do_facet mgs $LCTL get_param -N $mgs_exp.*); do
199                 [ $(do_facet mgs $LCTL get_param -n $exp_client_nid.uuid) == \
200                         $client_uuid ] &&
201                         break;
202         done
203         # save mgs export file to $temp_exp
204         do_facet mgs $LCTL get_param $exp_client_nid.export | tee $temp_exp
205
206         # Compare the value of field "connect_flags"
207         imp_val=$(grep "connect_flags" $temp_imp)
208         exp_val=$(grep "connect_flags" $temp_exp)
209         [ "$exp_val" == "$imp_val" ] ||
210                 error "export flags '$exp_val' != import flags '$imp_val'"
211
212         # Compare the value of client version
213         exp_client_version=$(awk '/target_version:/ { print $2 }' $temp_exp)
214         exp_val=$(version_code $exp_client_version)
215         imp_val=$CLIENT_VERSION
216         [ "$exp_val" == "$imp_val" ] ||
217                 error "export client version '$exp_val' != '$imp_val'"
218 }
219 run_test 0d "check export proc ============================="
220
221 test_1() {
222         test_mkdir $DIR/$tdir
223         test_mkdir $DIR/$tdir/d2
224         mkdir $DIR/$tdir/d2 && error "we expect EEXIST, but not returned"
225         $CHECKSTAT -t dir $DIR/$tdir/d2 || error "$tdir/d2 is not a dir"
226         rmdir $DIR/$tdir/d2
227         rmdir $DIR/$tdir
228         $CHECKSTAT -a $DIR/$tdir || error "$tdir was not removed"
229 }
230 run_test 1 "mkdir; remkdir; rmdir"
231
232 test_2() {
233         test_mkdir $DIR/$tdir
234         touch $DIR/$tdir/$tfile || error "touch $tdir/$tfile failed"
235         $CHECKSTAT -t file $DIR/$tdir/$tfile || error "$tdir/$tfile not a file"
236         rm -r $DIR/$tdir
237         $CHECKSTAT -a $DIR/$tdir/$tfile || error "$tdir/$file is not removed"
238 }
239 run_test 2 "mkdir; touch; rmdir; check file"
240
241 test_3() {
242         test_mkdir $DIR/$tdir
243         $CHECKSTAT -t dir $DIR/$tdir || error "$tdir is not a directory"
244         touch $DIR/$tdir/$tfile
245         $CHECKSTAT -t file $DIR/$tdir/$tfile || error "$tdir/$tfile not a file"
246         rm -r $DIR/$tdir
247         $CHECKSTAT -a $DIR/$tdir || error "$tdir is not removed"
248 }
249 run_test 3 "mkdir; touch; rmdir; check dir"
250
251 # LU-4471 - failed rmdir on remote directories still removes directory on MDT0
252 test_4() {
253         test_mkdir -i 1 $DIR/$tdir
254
255         touch $DIR/$tdir/$tfile ||
256                 error "Create file under remote directory failed"
257
258         rmdir $DIR/$tdir &&
259                 error "Expect error removing in-use dir $DIR/$tdir"
260
261         test -d $DIR/$tdir || error "Remote directory disappeared"
262
263         rm -rf $DIR/$tdir || error "remove remote dir error"
264 }
265 run_test 4 "mkdir; touch dir/file; rmdir; checkdir (expect error)"
266
267 test_5() {
268         test_mkdir $DIR/$tdir
269         test_mkdir $DIR/$tdir/d2
270         chmod 0707 $DIR/$tdir/d2 || error "chmod 0707 $tdir/d2 failed"
271         $CHECKSTAT -t dir -p 0707 $DIR/$tdir/d2 || error "$tdir/d2 not mode 707"
272         $CHECKSTAT -t dir $DIR/$tdir/d2 || error "$tdir/d2 is not a directory"
273 }
274 run_test 5 "mkdir .../d5 .../d5/d2; chmod .../d5/d2"
275
276 test_6a() {
277         touch $DIR/$tfile || error "touch $DIR/$tfile failed"
278         chmod 0666 $DIR/$tfile || error "chmod 0666 $tfile failed"
279         $CHECKSTAT -t file -p 0666 -u \#$UID $DIR/$tfile ||
280                 error "$tfile does not have perm 0666 or UID $UID"
281         $RUNAS chmod 0444 $DIR/$tfile && error "chmod $tfile worked on UID $UID"
282         $CHECKSTAT -t file -p 0666 -u \#$UID $DIR/$tfile ||
283                 error "$tfile should be 0666 and owned by UID $UID"
284 }
285 run_test 6a "touch f6a; chmod f6a; $RUNAS chmod f6a (should return error) =="
286
287 test_6c() {
288         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID"
289
290         touch $DIR/$tfile
291         chown $RUNAS_ID $DIR/$tfile || error "chown $RUNAS_ID $file failed"
292         $CHECKSTAT -t file -u \#$RUNAS_ID $DIR/$tfile ||
293                 error "$tfile should be owned by UID $RUNAS_ID"
294         $RUNAS chown $UID $DIR/$tfile && error "chown $UID $file succeeded"
295         $CHECKSTAT -t file -u \#$RUNAS_ID $DIR/$tfile ||
296                 error "$tfile should be owned by UID $RUNAS_ID"
297 }
298 run_test 6c "touch f6c; chown f6c; $RUNAS chown f6c (should return error) =="
299
300 test_6e() {
301         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID"
302
303         touch $DIR/$tfile
304         chgrp $RUNAS_ID $DIR/$tfile || error "chgrp $RUNAS_ID $file failed"
305         $CHECKSTAT -t file -u \#$UID -g \#$RUNAS_ID $DIR/$tfile ||
306                 error "$tfile should be owned by GID $UID"
307         $RUNAS chgrp $UID $DIR/$tfile && error "chgrp $UID $file succeeded"
308         $CHECKSTAT -t file -u \#$UID -g \#$RUNAS_ID $DIR/$tfile ||
309                 error "$tfile should be owned by UID $UID and GID $RUNAS_ID"
310 }
311 run_test 6e "touch+chgrp $tfile; $RUNAS chgrp $tfile (should return error)"
312
313 test_6g() {
314         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID"
315
316         test_mkdir $DIR/$tdir
317         chmod 777 $DIR/$tdir || error "chmod 0777 $tdir failed"
318         $RUNAS mkdir $DIR/$tdir/d || error "mkdir $tdir/d failed"
319         chmod g+s $DIR/$tdir/d || error "chmod g+s $tdir/d failed"
320         test_mkdir $DIR/$tdir/d/subdir
321         $CHECKSTAT -g \#$RUNAS_GID $DIR/$tdir/d/subdir ||
322                 error "$tdir/d/subdir should be GID $RUNAS_GID"
323         if [[ $MDSCOUNT -gt 1 ]]; then
324                 # check remote dir sgid inherite
325                 $LFS mkdir -i 0 $DIR/$tdir.local ||
326                         error "mkdir $tdir.local failed"
327                 chmod g+s $DIR/$tdir.local ||
328                         error "chmod $tdir.local failed"
329                 chgrp $RUNAS_GID $DIR/$tdir.local ||
330                         error "chgrp $tdir.local failed"
331                 $LFS mkdir -i 1 $DIR/$tdir.local/$tdir.remote ||
332                         error "mkdir $tdir.remote failed"
333                 $CHECKSTAT -g \#$RUNAS_GID $DIR/$tdir.local/$tdir.remote ||
334                         error "$tdir.remote should be owned by $UID.$RUNAS_ID"
335                 $CHECKSTAT -p 02755 $DIR/$tdir.local/$tdir.remote ||
336                         error "$tdir.remote should be mode 02755"
337         fi
338 }
339 run_test 6g "verify new dir in sgid dir inherits group"
340
341 test_6h() { # bug 7331
342         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID"
343
344         touch $DIR/$tfile || error "touch failed"
345         chown $RUNAS_ID:$RUNAS_GID $DIR/$tfile || error "initial chown failed"
346         $RUNAS -G$RUNAS_GID chown $RUNAS_ID:0 $DIR/$tfile &&
347                 error "chown $RUNAS_ID:0 $tfile worked as GID $RUNAS_GID"
348         $CHECKSTAT -t file -u \#$RUNAS_ID -g \#$RUNAS_GID $DIR/$tfile ||
349                 error "$tdir/$tfile should be UID $RUNAS_UID GID $RUNAS_GID"
350 }
351 run_test 6h "$RUNAS chown RUNAS_ID.0 .../$tfile (should return error)"
352
353 test_7a() {
354         test_mkdir $DIR/$tdir
355         $MCREATE $DIR/$tdir/$tfile
356         chmod 0666 $DIR/$tdir/$tfile
357         $CHECKSTAT -t file -p 0666 $DIR/$tdir/$tfile ||
358                 error "$tdir/$tfile should be mode 0666"
359 }
360 run_test 7a "mkdir .../d7; mcreate .../d7/f; chmod .../d7/f ===="
361
362 test_7b() {
363         if [ ! -d $DIR/$tdir ]; then
364                 test_mkdir $DIR/$tdir
365         fi
366         $MCREATE $DIR/$tdir/$tfile
367         echo -n foo > $DIR/$tdir/$tfile
368         [ "$(cat $DIR/$tdir/$tfile)" = "foo" ] || error "$tdir/$tfile not 'foo'"
369         $CHECKSTAT -t file -s 3 $DIR/$tdir/$tfile || error "$tfile size not 3"
370 }
371 run_test 7b "mkdir .../d7; mcreate d7/f2; echo foo > d7/f2 ====="
372
373 test_8() {
374         test_mkdir $DIR/$tdir
375         touch $DIR/$tdir/$tfile
376         chmod 0666 $DIR/$tdir/$tfile
377         $CHECKSTAT -t file -p 0666 $DIR/$tdir/$tfile ||
378                 error "$tfile mode not 0666"
379 }
380 run_test 8 "mkdir .../d8; touch .../d8/f; chmod .../d8/f ======="
381
382 test_9() {
383         test_mkdir $DIR/$tdir
384         test_mkdir $DIR/$tdir/d2
385         test_mkdir $DIR/$tdir/d2/d3
386         $CHECKSTAT -t dir $DIR/$tdir/d2/d3 || error "$tdir/d2/d3 not a dir"
387 }
388 run_test 9 "mkdir .../d9 .../d9/d2 .../d9/d2/d3 ================"
389
390 test_10() {
391         test_mkdir $DIR/$tdir
392         test_mkdir $DIR/$tdir/d2
393         touch $DIR/$tdir/d2/$tfile
394         $CHECKSTAT -t file $DIR/$tdir/d2/$tfile ||
395                 error "$tdir/d2/$tfile not a file"
396 }
397 run_test 10 "mkdir .../d10 .../d10/d2; touch .../d10/d2/f ======"
398
399 test_11() {
400         test_mkdir $DIR/$tdir
401         test_mkdir $DIR/$tdir/d2
402         chmod 0666 $DIR/$tdir/d2
403         chmod 0705 $DIR/$tdir/d2
404         $CHECKSTAT -t dir -p 0705 $DIR/$tdir/d2 ||
405                 error "$tdir/d2 mode not 0705"
406 }
407 run_test 11 "mkdir .../d11 d11/d2; chmod .../d11/d2 ============"
408
409 test_12() {
410         test_mkdir $DIR/$tdir
411         touch $DIR/$tdir/$tfile
412         chmod 0666 $DIR/$tdir/$tfile
413         chmod 0654 $DIR/$tdir/$tfile
414         $CHECKSTAT -t file -p 0654 $DIR/$tdir/$tfile ||
415                 error "$tdir/d2 mode not 0654"
416 }
417 run_test 12 "touch .../d12/f; chmod .../d12/f .../d12/f ========"
418
419 test_13() {
420         test_mkdir $DIR/$tdir
421         dd if=/dev/zero of=$DIR/$tdir/$tfile count=10
422         >  $DIR/$tdir/$tfile
423         $CHECKSTAT -t file -s 0 $DIR/$tdir/$tfile ||
424                 error "$tdir/$tfile size not 0 after truncate"
425 }
426 run_test 13 "creat .../d13/f; dd .../d13/f; > .../d13/f ========"
427
428 test_14() {
429         test_mkdir $DIR/$tdir
430         touch $DIR/$tdir/$tfile
431         rm $DIR/$tdir/$tfile
432         $CHECKSTAT -a $DIR/$tdir/$tfile || error "$tdir/$tfile not removed"
433 }
434 run_test 14 "touch .../d14/f; rm .../d14/f; rm .../d14/f ======="
435
436 test_15() {
437         test_mkdir $DIR/$tdir
438         touch $DIR/$tdir/$tfile
439         mv $DIR/$tdir/$tfile $DIR/$tdir/${tfile}_2
440         $CHECKSTAT -t file $DIR/$tdir/${tfile}_2 ||
441                 error "$tdir/${tfile_2} not a file after rename"
442         rm $DIR/$tdir/${tfile}_2 || error "unlink failed after rename"
443 }
444 run_test 15 "touch .../d15/f; mv .../d15/f .../d15/f2 =========="
445
446 test_16() {
447         test_mkdir $DIR/$tdir
448         touch $DIR/$tdir/$tfile
449         rm -rf $DIR/$tdir/$tfile
450         $CHECKSTAT -a $DIR/$tdir/$tfile || error "$tdir/$tfile not removed"
451 }
452 run_test 16 "touch .../d16/f; rm -rf .../d16/f"
453
454 test_17a() {
455         test_mkdir $DIR/$tdir
456         touch $DIR/$tdir/$tfile
457         ln -s $DIR/$tdir/$tfile $DIR/$tdir/l-exist
458         ls -l $DIR/$tdir
459         $CHECKSTAT -l $DIR/$tdir/$tfile $DIR/$tdir/l-exist ||
460                 error "$tdir/l-exist not a symlink"
461         $CHECKSTAT -f -t f $DIR/$tdir/l-exist ||
462                 error "$tdir/l-exist not referencing a file"
463         rm -f $DIR/$tdir/l-exist
464         $CHECKSTAT -a $DIR/$tdir/l-exist || error "$tdir/l-exist not removed"
465 }
466 run_test 17a "symlinks: create, remove (real)"
467
468 test_17b() {
469         test_mkdir $DIR/$tdir
470         ln -s no-such-file $DIR/$tdir/l-dangle
471         ls -l $DIR/$tdir
472         $CHECKSTAT -l no-such-file $DIR/$tdir/l-dangle ||
473                 error "$tdir/l-dangle not referencing no-such-file"
474         $CHECKSTAT -fa $DIR/$tdir/l-dangle ||
475                 error "$tdir/l-dangle not referencing non-existent file"
476         rm -f $DIR/$tdir/l-dangle
477         $CHECKSTAT -a $DIR/$tdir/l-dangle || error "$tdir/l-dangle not removed"
478 }
479 run_test 17b "symlinks: create, remove (dangling)"
480
481 test_17c() { # bug 3440 - don't save failed open RPC for replay
482         test_mkdir $DIR/$tdir
483         ln -s foo $DIR/$tdir/$tfile
484         cat $DIR/$tdir/$tfile && error "opened non-existent symlink" || true
485 }
486 run_test 17c "symlinks: open dangling (should return error)"
487
488 test_17d() {
489         test_mkdir $DIR/$tdir
490         ln -s foo $DIR/$tdir/$tfile
491         touch $DIR/$tdir/$tfile || error "creating to new symlink"
492 }
493 run_test 17d "symlinks: create dangling"
494
495 test_17e() {
496         test_mkdir $DIR/$tdir
497         local foo=$DIR/$tdir/$tfile
498         ln -s $foo $foo || error "create symlink failed"
499         ls -l $foo || error "ls -l failed"
500         ls $foo && error "ls not failed" || true
501 }
502 run_test 17e "symlinks: create recursive symlink (should return error)"
503
504 test_17f() {
505         test_mkdir $DIR/$tdir
506         ln -s 1234567890/2234567890/3234567890/4234567890 $DIR/$tdir/111
507         ln -s 1234567890/2234567890/3234567890/4234567890/5234567890/6234567890 $DIR/$tdir/222
508         ln -s 1234567890/2234567890/3234567890/4234567890/5234567890/6234567890/7234567890/8234567890 $DIR/$tdir/333
509         ln -s 1234567890/2234567890/3234567890/4234567890/5234567890/6234567890/7234567890/8234567890/9234567890/a234567890/b234567890 $DIR/$tdir/444
510         ln -s 1234567890/2234567890/3234567890/4234567890/5234567890/6234567890/7234567890/8234567890/9234567890/a234567890/b234567890/c234567890/d234567890/f234567890 $DIR/$tdir/555
511         ln -s 1234567890/2234567890/3234567890/4234567890/5234567890/6234567890/7234567890/8234567890/9234567890/a234567890/b234567890/c234567890/d234567890/f234567890/aaaaaaaaaa/bbbbbbbbbb/cccccccccc/dddddddddd/eeeeeeeeee/ffffffffff/ $DIR/$tdir/666
512         ls -l  $DIR/$tdir
513 }
514 run_test 17f "symlinks: long and very long symlink name"
515
516 # str_repeat(S, N) generate a string that is string S repeated N times
517 str_repeat() {
518         local s=$1
519         local n=$2
520         local ret=''
521         while [ $((n -= 1)) -ge 0 ]; do
522                 ret=$ret$s
523         done
524         echo $ret
525 }
526
527 # Long symlinks and LU-2241
528 test_17g() {
529         test_mkdir $DIR/$tdir
530         local TESTS="59 60 61 4094 4095"
531
532         # Fix for inode size boundary in 2.1.4
533         [ $MDS1_VERSION -lt $(version_code 2.1.4) ] &&
534                 TESTS="4094 4095"
535
536         # Patch not applied to 2.2 or 2.3 branches
537         [ $MDS1_VERSION -ge $(version_code 2.2.0) ] &&
538         [ $MDS1_VERSION -le $(version_code 2.3.55) ] &&
539                 TESTS="4094 4095"
540
541         # skip long symlink name for rhel6.5.
542         # rhel6.5 has a limit (PATH_MAX - sizeof(struct filename))
543         grep -q '6.5' /etc/redhat-release &>/dev/null &&
544                 TESTS="59 60 61 4062 4063"
545
546         for i in $TESTS; do
547                 local SYMNAME=$(str_repeat 'x' $i)
548                 ln -s $SYMNAME $DIR/$tdir/f$i || error "failed $i-char symlink"
549                 readlink $DIR/$tdir/f$i || error "failed $i-char readlink"
550         done
551 }
552 run_test 17g "symlinks: really long symlink name and inode boundaries"
553
554 test_17h() { #bug 17378
555         [ $PARALLEL == "yes" ] && skip "skip parallel run"
556         remote_mds_nodsh && skip "remote MDS with nodsh"
557
558         local mdt_idx
559
560         test_mkdir $DIR/$tdir
561         mdt_idx=$($LFS getdirstripe -i $DIR/$tdir)
562         $LFS setstripe -c -1 $DIR/$tdir
563         #define OBD_FAIL_MDS_LOV_PREP_CREATE 0x141
564         do_facet mds$((mdt_idx + 1)) lctl set_param fail_loc=0x80000141
565         touch $DIR/$tdir/$tfile || true
566 }
567 run_test 17h "create objects: lov_free_memmd() doesn't lbug"
568
569 test_17i() { #bug 20018
570         [ $PARALLEL == "yes" ] && skip "skip parallel run"
571         remote_mds_nodsh && skip "remote MDS with nodsh"
572
573         local foo=$DIR/$tdir/$tfile
574         local mdt_idx
575
576         test_mkdir -c1 $DIR/$tdir
577         mdt_idx=$($LFS getdirstripe -i $DIR/$tdir)
578         ln -s $foo $foo || error "create symlink failed"
579 #define OBD_FAIL_MDS_READLINK_EPROTO     0x143
580         do_facet mds$((mdt_idx + 1)) lctl set_param fail_loc=0x80000143
581         ls -l $foo && error "error not detected"
582         return 0
583 }
584 run_test 17i "don't panic on short symlink (should return error)"
585
586 test_17k() { #bug 22301
587         [ $PARALLEL == "yes" ] && skip "skip parallel run"
588         [[ -z "$(which rsync 2>/dev/null)" ]] &&
589                 skip "no rsync command"
590         rsync --help | grep -q xattr ||
591                 skip_env "$(rsync --version | head -n1) does not support xattrs"
592         test_mkdir $DIR/$tdir
593         test_mkdir $DIR/$tdir.new
594         touch $DIR/$tdir/$tfile
595         ln -s $DIR/$tdir/$tfile $DIR/$tdir/$tfile.lnk
596         rsync -av -X $DIR/$tdir/ $DIR/$tdir.new ||
597                 error "rsync failed with xattrs enabled"
598 }
599 run_test 17k "symlinks: rsync with xattrs enabled"
600
601 test_17l() { # LU-279
602         [[ -z "$(which getfattr 2>/dev/null)" ]] &&
603                 skip "no getfattr command"
604
605         test_mkdir $DIR/$tdir
606         touch $DIR/$tdir/$tfile
607         ln -s $DIR/$tdir/$tfile $DIR/$tdir/$tfile.lnk
608         for path in "$DIR/$tdir" "$DIR/$tdir/$tfile" "$DIR/$tdir/$tfile.lnk"; do
609                 # -h to not follow symlinks. -m '' to list all the xattrs.
610                 # grep to remove first line: '# file: $path'.
611                 for xattr in `getfattr -hm '' $path 2>/dev/null | grep -v '^#'`;
612                 do
613                         lgetxattr_size_check $path $xattr ||
614                                 error "lgetxattr_size_check $path $xattr failed"
615                 done
616         done
617 }
618 run_test 17l "Ensure lgetxattr's returned xattr size is consistent"
619
620 # LU-1540
621 test_17m() {
622         [ $PARALLEL == "yes" ] && skip "skip parallel run"
623         [ "$mds1_FSTYPE" != "ldiskfs" ] && skip_env "ldiskfs only test"
624         remote_mds_nodsh && skip "remote MDS with nodsh"
625         [ $MDS1_VERSION -ge $(version_code 2.2.0) ] &&
626         [ $MDS1_VERSION -le $(version_code 2.2.93) ] &&
627                 skip "MDS 2.2.0-2.2.93 do not NUL-terminate symlinks"
628
629         local short_sym="0123456789"
630         local wdir=$DIR/$tdir
631         local i
632
633         test_mkdir $wdir
634         long_sym=$short_sym
635         # create a long symlink file
636         for ((i = 0; i < 4; ++i)); do
637                 long_sym=${long_sym}${long_sym}
638         done
639
640         echo "create 512 short and long symlink files under $wdir"
641         for ((i = 0; i < 256; ++i)); do
642                 ln -sf ${long_sym}"a5a5" $wdir/long-$i
643                 ln -sf ${short_sym}"a5a5" $wdir/short-$i
644         done
645
646         echo "erase them"
647         rm -f $wdir/*
648         sync
649         wait_delete_completed
650
651         echo "recreate the 512 symlink files with a shorter string"
652         for ((i = 0; i < 512; ++i)); do
653                 # rewrite the symlink file with a shorter string
654                 ln -sf ${long_sym} $wdir/long-$i || error "long_sym failed"
655                 ln -sf ${short_sym} $wdir/short-$i || error "short_sym failed"
656         done
657
658         local mds_index=$(($($LFS getstripe -m $wdir) + 1))
659         local devname=$(mdsdevname $mds_index)
660
661         echo "stop and checking mds${mds_index}:"
662         # e2fsck should not return error
663         stop mds${mds_index}
664         run_e2fsck $(facet_active_host mds${mds_index}) $devname -n
665         rc=$?
666
667         start mds${mds_index} $devname $MDS_MOUNT_OPTS ||
668                 error "start mds${mds_index} failed"
669         df $MOUNT > /dev/null 2>&1
670         [ $rc -eq 0 ] ||
671                 error "e2fsck detected error for short/long symlink: rc=$rc"
672         rm -f $wdir/*
673 }
674 run_test 17m "run e2fsck against MDT which contains short/long symlink"
675
676 check_fs_consistency_17n() {
677         local mdt_index
678         local rc=0
679
680         # create/unlink in 17n only change 2 MDTs(MDT1/MDT2),
681         # so it only check MDT1/MDT2 instead of all of MDTs.
682         for mdt_index in 1 2; do
683                 local devname=$(mdsdevname $mdt_index)
684                 # e2fsck should not return error
685                 stop mds${mdt_index}
686                 run_e2fsck $(facet_active_host mds$mdt_index) $devname -n ||
687                         rc=$((rc + $?))
688
689                 start mds${mdt_index} $devname $MDS_MOUNT_OPTS ||
690                         error "mount mds$mdt_index failed"
691                 df $MOUNT > /dev/null 2>&1
692         done
693         return $rc
694 }
695
696 test_17n() {
697         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 2 MDTs"
698         [ $PARALLEL == "yes" ] && skip "skip parallel run"
699         [ "$mds1_FSTYPE" != "ldiskfs" ] && skip_env "ldiskfs only test"
700         remote_mds_nodsh && skip "remote MDS with nodsh"
701         [ $MDS1_VERSION -ge $(version_code 2.2.0) ] &&
702         [ $MDS1_VERSION -le $(version_code 2.2.93) ] &&
703                 skip "MDS 2.2.0-2.2.93 do not NUL-terminate symlinks"
704
705         local i
706
707         test_mkdir $DIR/$tdir
708         for ((i=0; i<10; i++)); do
709                 $LFS mkdir -i1 -c2 $DIR/$tdir/remote_dir_${i} ||
710                         error "create remote dir error $i"
711                 createmany -o $DIR/$tdir/remote_dir_${i}/f 10 ||
712                         error "create files under remote dir failed $i"
713         done
714
715         check_fs_consistency_17n ||
716                 error "e2fsck report error after create files under remote dir"
717
718         for ((i = 0; i < 10; i++)); do
719                 rm -rf $DIR/$tdir/remote_dir_${i} ||
720                         error "destroy remote dir error $i"
721         done
722
723         check_fs_consistency_17n ||
724                 error "e2fsck report error after unlink files under remote dir"
725
726         [ $MDS1_VERSION -lt $(version_code 2.4.50) ] &&
727                 skip "lustre < 2.4.50 does not support migrate mv"
728
729         for ((i = 0; i < 10; i++)); do
730                 mkdir -p $DIR/$tdir/remote_dir_${i}
731                 createmany -o $DIR/$tdir/remote_dir_${i}/f 10 ||
732                         error "create files under remote dir failed $i"
733                 $LFS migrate --mdt-index 1 $DIR/$tdir/remote_dir_${i} ||
734                         error "migrate remote dir error $i"
735         done
736         check_fs_consistency_17n || error "e2fsck report error after migration"
737
738         for ((i = 0; i < 10; i++)); do
739                 rm -rf $DIR/$tdir/remote_dir_${i} ||
740                         error "destroy remote dir error $i"
741         done
742
743         check_fs_consistency_17n || error "e2fsck report error after unlink"
744 }
745 run_test 17n "run e2fsck against master/slave MDT which contains remote dir"
746
747 test_17o() {
748         remote_mds_nodsh && skip "remote MDS with nodsh"
749         [ $MDS1_VERSION -lt $(version_code 2.3.64) ] &&
750                 skip "Need MDS version at least 2.3.64"
751
752         local wdir=$DIR/${tdir}o
753         local mdt_index
754         local rc=0
755
756         test_mkdir $wdir
757         touch $wdir/$tfile
758         mdt_index=$($LFS getstripe -m $wdir/$tfile)
759         mdt_index=$((mdt_index + 1))
760
761         cancel_lru_locks mdc
762         #fail mds will wait the failover finish then set
763         #following fail_loc to avoid interfer the recovery process.
764         fail mds${mdt_index}
765
766         #define OBD_FAIL_OSD_LMA_INCOMPAT 0x194
767         do_facet mds${mdt_index} lctl set_param fail_loc=0x194
768         ls -l $wdir/$tfile && rc=1
769         do_facet mds${mdt_index} lctl set_param fail_loc=0
770         [[ $rc -eq 0 ]] || error "stat file should fail"
771 }
772 run_test 17o "stat file with incompat LMA feature"
773
774 test_18() {
775         touch $DIR/$tfile || error "Failed to touch $DIR/$tfile: $?"
776         ls $DIR || error "Failed to ls $DIR: $?"
777 }
778 run_test 18 "touch .../f ; ls ... =============================="
779
780 test_19a() {
781         touch $DIR/$tfile
782         ls -l $DIR
783         rm $DIR/$tfile
784         $CHECKSTAT -a $DIR/$tfile || error "$tfile was not removed"
785 }
786 run_test 19a "touch .../f19 ; ls -l ... ; rm .../f19 ==========="
787
788 test_19b() {
789         ls -l $DIR/$tfile && error "ls -l $tfile failed"|| true
790 }
791 run_test 19b "ls -l .../f19 (should return error) =============="
792
793 test_19c() {
794         [ $RUNAS_ID -eq $UID ] &&
795                 skip_env "RUNAS_ID = UID = $UID -- skipping"
796
797         $RUNAS touch $DIR/$tfile && error "create non-root file failed" || true
798 }
799 run_test 19c "$RUNAS touch .../f19 (should return error) =="
800
801 test_19d() {
802         cat $DIR/f19 && error || true
803 }
804 run_test 19d "cat .../f19 (should return error) =============="
805
806 test_20() {
807         touch $DIR/$tfile
808         rm $DIR/$tfile
809         touch $DIR/$tfile
810         rm $DIR/$tfile
811         touch $DIR/$tfile
812         rm $DIR/$tfile
813         $CHECKSTAT -a $DIR/$tfile || error "$tfile was not removed"
814 }
815 run_test 20 "touch .../f ; ls -l ..."
816
817 test_21() {
818         test_mkdir $DIR/$tdir
819         [ -f $DIR/$tdir/dangle ] && rm -f $DIR/$tdir/dangle
820         ln -s dangle $DIR/$tdir/link
821         echo foo >> $DIR/$tdir/link
822         cat $DIR/$tdir/dangle
823         $CHECKSTAT -t link $DIR/$tdir/link || error "$tdir/link not a link"
824         $CHECKSTAT -f -t file $DIR/$tdir/link ||
825                 error "$tdir/link not linked to a file"
826 }
827 run_test 21 "write to dangling link"
828
829 test_22() {
830         local wdir=$DIR/$tdir
831         test_mkdir $wdir
832         chown $RUNAS_ID:$RUNAS_GID $wdir
833         (cd $wdir || error "cd $wdir failed";
834                 $RUNAS tar cf - /etc/hosts /etc/sysconfig/network |
835                 $RUNAS tar xf -)
836         ls -lR $wdir/etc || error "ls -lR $wdir/etc failed"
837         $CHECKSTAT -t dir $wdir/etc || error "checkstat -t dir failed"
838         $CHECKSTAT -u \#$RUNAS_ID -g \#$RUNAS_GID $wdir/etc ||
839                 error "checkstat -u failed"
840 }
841 run_test 22 "unpack tar archive as non-root user"
842
843 # was test_23
844 test_23a() {
845         test_mkdir $DIR/$tdir
846         local file=$DIR/$tdir/$tfile
847
848         openfile -f O_CREAT:O_EXCL $file || error "$file create failed"
849         openfile -f O_CREAT:O_EXCL $file &&
850                 error "$file recreate succeeded" || true
851 }
852 run_test 23a "O_CREAT|O_EXCL in subdir"
853
854 test_23b() { # bug 18988
855         test_mkdir $DIR/$tdir
856         local file=$DIR/$tdir/$tfile
857
858         rm -f $file
859         echo foo > $file || error "write filed"
860         echo bar >> $file || error "append filed"
861         $CHECKSTAT -s 8 $file || error "wrong size"
862         rm $file
863 }
864 run_test 23b "O_APPEND check"
865
866 # LU-9409, size with O_APPEND and tiny writes
867 test_23c() {
868         local file=$DIR/$tfile
869
870         # single dd
871         dd conv=notrunc oflag=append if=/dev/zero of=$file bs=8 count=800
872         $CHECKSTAT -s 6400 $file || error "wrong size, expected 6400"
873         rm -f $file
874
875         # racing tiny writes
876         dd conv=notrunc oflag=append if=/dev/zero of=$file bs=8 count=800 &
877         dd conv=notrunc oflag=append if=/dev/zero of=$file bs=8 count=800 &
878         wait
879         $CHECKSTAT -s 12800 $file || error "wrong size, expected 12800"
880         rm -f $file
881
882         #racing tiny & normal writes
883         dd conv=notrunc oflag=append if=/dev/zero of=$file bs=4096 count=4 &
884         dd conv=notrunc oflag=append if=/dev/zero of=$file bs=8 count=100 &
885         wait
886         $CHECKSTAT -s 17184 $file || error "wrong size, expected 17184"
887         rm -f $file
888
889         #racing tiny & normal writes 2, ugly numbers
890         dd conv=notrunc oflag=append if=/dev/zero of=$file bs=4099 count=11 &
891         dd conv=notrunc oflag=append if=/dev/zero of=$file bs=17 count=173 &
892         wait
893         $CHECKSTAT -s 48030 $file || error "wrong size, expected 48030"
894         rm -f $file
895 }
896 run_test 23c "O_APPEND size checks for tiny writes"
897
898 # LU-11069 file offset is correct after appending writes
899 test_23d() {
900         local file=$DIR/$tfile
901         local offset
902
903         echo CentaurHauls > $file
904         offset=$($MULTIOP $file oO_WRONLY:O_APPEND:w13Zp)
905         if ((offset != 26)); then
906                 error "wrong offset, expected 26, got '$offset'"
907         fi
908 }
909 run_test 23d "file offset is correct after appending writes"
910
911 # rename sanity
912 test_24a() {
913         echo '-- same directory rename'
914         test_mkdir $DIR/$tdir
915         touch $DIR/$tdir/$tfile.1
916         mv $DIR/$tdir/$tfile.1 $DIR/$tdir/$tfile.2
917         $CHECKSTAT -t file $DIR/$tdir/$tfile.2 || error "$tfile.2 not a file"
918 }
919 run_test 24a "rename file to non-existent target"
920
921 test_24b() {
922         test_mkdir $DIR/$tdir
923         touch $DIR/$tdir/$tfile.{1,2}
924         mv $DIR/$tdir/$tfile.1 $DIR/$tdir/$tfile.2
925         $CHECKSTAT -a $DIR/$tdir/$tfile.1 || error "$tfile.1 exists"
926         $CHECKSTAT -t file $DIR/$tdir/$tfile.2 || error "$tfile.2 not a file"
927 }
928 run_test 24b "rename file to existing target"
929
930 test_24c() {
931         test_mkdir $DIR/$tdir
932         test_mkdir $DIR/$tdir/d$testnum.1
933         mv $DIR/$tdir/d$testnum.1 $DIR/$tdir/d$testnum.2
934         $CHECKSTAT -a $DIR/$tdir/d$testnum.1 || error "d$testnum.1 exists"
935         $CHECKSTAT -t dir $DIR/$tdir/d$testnum.2 || error "d$testnum.2 not dir"
936 }
937 run_test 24c "rename directory to non-existent target"
938
939 test_24d() {
940         test_mkdir -c1 $DIR/$tdir
941         test_mkdir -c1 $DIR/$tdir/d$testnum.1
942         test_mkdir -c1 $DIR/$tdir/d$testnum.2
943         mrename $DIR/$tdir/d$testnum.1 $DIR/$tdir/d$testnum.2
944         $CHECKSTAT -a $DIR/$tdir/d$testnum.1 || error "d$testnum.1 exists"
945         $CHECKSTAT -t dir $DIR/$tdir/d$testnum.2 || error "d$testnum.2 not dir"
946 }
947 run_test 24d "rename directory to existing target"
948
949 test_24e() {
950         echo '-- cross directory renames --'
951         test_mkdir $DIR/R5a
952         test_mkdir $DIR/R5b
953         touch $DIR/R5a/f
954         mv $DIR/R5a/f $DIR/R5b/g
955         $CHECKSTAT -a $DIR/R5a/f || error "$DIR/R5a/f exists"
956         $CHECKSTAT -t file $DIR/R5b/g || error "$DIR/R5b/g not file type"
957 }
958 run_test 24e "touch .../R5a/f; rename .../R5a/f .../R5b/g ======"
959
960 test_24f() {
961         test_mkdir $DIR/R6a
962         test_mkdir $DIR/R6b
963         touch $DIR/R6a/f $DIR/R6b/g
964         mv $DIR/R6a/f $DIR/R6b/g
965         $CHECKSTAT -a $DIR/R6a/f || error "$DIR/R6a/f exists"
966         $CHECKSTAT -t file $DIR/R6b/g || error "$DIR/R6b/g not file type"
967 }
968 run_test 24f "touch .../R6a/f R6b/g; mv .../R6a/f .../R6b/g ===="
969
970 test_24g() {
971         test_mkdir $DIR/R7a
972         test_mkdir $DIR/R7b
973         test_mkdir $DIR/R7a/d
974         mv $DIR/R7a/d $DIR/R7b/e
975         $CHECKSTAT -a $DIR/R7a/d || error "$DIR/R7a/d exists"
976         $CHECKSTAT -t dir $DIR/R7b/e || error "$DIR/R7b/e not dir type"
977 }
978 run_test 24g "mkdir .../R7{a,b}/d; mv .../R7a/d .../R7b/e ======"
979
980 test_24h() {
981         test_mkdir -c1 $DIR/R8a
982         test_mkdir -c1 $DIR/R8b
983         test_mkdir -c1 $DIR/R8a/d
984         test_mkdir -c1 $DIR/R8b/e
985         mrename $DIR/R8a/d $DIR/R8b/e
986         $CHECKSTAT -a $DIR/R8a/d || error "$DIR/R8a/d exists"
987         $CHECKSTAT -t dir $DIR/R8b/e || error "$DIR/R8b/e not dir type"
988 }
989 run_test 24h "mkdir .../R8{a,b}/{d,e}; rename .../R8a/d .../R8b/e"
990
991 test_24i() {
992         echo "-- rename error cases"
993         test_mkdir $DIR/R9
994         test_mkdir $DIR/R9/a
995         touch $DIR/R9/f
996         mrename $DIR/R9/f $DIR/R9/a
997         $CHECKSTAT -t file $DIR/R9/f || error "$DIR/R9/f not file type"
998         $CHECKSTAT -t dir  $DIR/R9/a || error "$DIR/R9/a not dir type"
999         $CHECKSTAT -a $DIR/R9/a/f || error "$DIR/R9/a/f exists"
1000 }
1001 run_test 24i "rename file to dir error: touch f ; mkdir a ; rename f a"
1002
1003 test_24j() {
1004         test_mkdir $DIR/R10
1005         mrename $DIR/R10/f $DIR/R10/g
1006         $CHECKSTAT -t dir $DIR/R10 || error "$DIR/R10 not dir type"
1007         $CHECKSTAT -a $DIR/R10/f || error "$DIR/R10/f exists"
1008         $CHECKSTAT -a $DIR/R10/g || error "$DIR/R10/g exists"
1009 }
1010 run_test 24j "source does not exist ============================"
1011
1012 test_24k() {
1013         test_mkdir $DIR/R11a
1014         test_mkdir $DIR/R11a/d
1015         touch $DIR/R11a/f
1016         mv $DIR/R11a/f $DIR/R11a/d
1017         $CHECKSTAT -a $DIR/R11a/f || error "$DIR/R11a/f exists"
1018         $CHECKSTAT -t file $DIR/R11a/d/f || error "$DIR/R11a/d/f not file type"
1019 }
1020 run_test 24k "touch .../R11a/f; mv .../R11a/f .../R11a/d ======="
1021
1022 # bug 2429 - rename foo foo foo creates invalid file
1023 test_24l() {
1024         f="$DIR/f24l"
1025         $MULTIOP $f OcNs || error "rename of ${f} to itself failed"
1026 }
1027 run_test 24l "Renaming a file to itself ========================"
1028
1029 test_24m() {
1030         f="$DIR/f24m"
1031         $MULTIOP $f OcLN ${f}2 ${f}2 || error "link ${f}2 ${f}2 failed"
1032         # on ext3 this does not remove either the source or target files
1033         # though the "expected" operation would be to remove the source
1034         $CHECKSTAT -t file ${f} || error "${f} missing"
1035         $CHECKSTAT -t file ${f}2 || error "${f}2 missing"
1036 }
1037 run_test 24m "Renaming a file to a hard link to itself ========="
1038
1039 test_24n() {
1040     f="$DIR/f24n"
1041     # this stats the old file after it was renamed, so it should fail
1042     touch ${f}
1043     $CHECKSTAT ${f} || error "${f} missing"
1044     mv ${f} ${f}.rename
1045     $CHECKSTAT ${f}.rename || error "${f}.rename missing"
1046     $CHECKSTAT -a ${f} || error "${f} exists"
1047 }
1048 run_test 24n "Statting the old file after renaming (Posix rename 2)"
1049
1050 test_24o() {
1051         test_mkdir $DIR/$tdir
1052         rename_many -s random -v -n 10 $DIR/$tdir
1053 }
1054 run_test 24o "rename of files during htree split"
1055
1056 test_24p() {
1057         test_mkdir $DIR/R12a
1058         test_mkdir $DIR/R12b
1059         DIRINO=`ls -lid $DIR/R12a | awk '{ print $1 }'`
1060         mrename $DIR/R12a $DIR/R12b
1061         $CHECKSTAT -a $DIR/R12a || error "$DIR/R12a exists"
1062         $CHECKSTAT -t dir $DIR/R12b || error "$DIR/R12b not dir type"
1063         DIRINO2=`ls -lid $DIR/R12b | awk '{ print $1 }'`
1064         [ "$DIRINO" = "$DIRINO2" ] || error "R12a $DIRINO != R12b $DIRINO2"
1065 }
1066 run_test 24p "mkdir .../R12{a,b}; rename .../R12a .../R12b"
1067
1068 cleanup_multiop_pause() {
1069         trap 0
1070         kill -USR1 $MULTIPID
1071 }
1072
1073 test_24q() {
1074         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1075
1076         test_mkdir $DIR/R13a
1077         test_mkdir $DIR/R13b
1078         local DIRINO=$(ls -lid $DIR/R13a | awk '{ print $1 }')
1079         multiop_bg_pause $DIR/R13b D_c || error "multiop failed to start"
1080         MULTIPID=$!
1081
1082         trap cleanup_multiop_pause EXIT
1083         mrename $DIR/R13a $DIR/R13b
1084         $CHECKSTAT -a $DIR/R13a || error "R13a still exists"
1085         $CHECKSTAT -t dir $DIR/R13b || error "R13b does not exist"
1086         local DIRINO2=$(ls -lid $DIR/R13b | awk '{ print $1 }')
1087         [ "$DIRINO" = "$DIRINO2" ] || error "R13a $DIRINO != R13b $DIRINO2"
1088         cleanup_multiop_pause
1089         wait $MULTIPID || error "multiop close failed"
1090 }
1091 run_test 24q "mkdir .../R13{a,b}; open R13b rename R13a R13b ==="
1092
1093 test_24r() { #bug 3789
1094         test_mkdir $DIR/R14a
1095         test_mkdir $DIR/R14a/b
1096         mrename $DIR/R14a $DIR/R14a/b && error "rename to subdir worked!"
1097         $CHECKSTAT -t dir $DIR/R14a || error "$DIR/R14a missing"
1098         $CHECKSTAT -t dir $DIR/R14a/b || error "$DIR/R14a/b missing"
1099 }
1100 run_test 24r "mkdir .../R14a/b; rename .../R14a .../R14a/b ====="
1101
1102 test_24s() {
1103         test_mkdir $DIR/R15a
1104         test_mkdir $DIR/R15a/b
1105         test_mkdir $DIR/R15a/b/c
1106         mrename $DIR/R15a $DIR/R15a/b/c && error "rename to sub-subdir worked!"
1107         $CHECKSTAT -t dir $DIR/R15a || error "$DIR/R15a missing"
1108         $CHECKSTAT -t dir $DIR/R15a/b/c || error "$DIR/R15a/b/c missing"
1109 }
1110 run_test 24s "mkdir .../R15a/b/c; rename .../R15a .../R15a/b/c ="
1111 test_24t() {
1112         test_mkdir $DIR/R16a
1113         test_mkdir $DIR/R16a/b
1114         test_mkdir $DIR/R16a/b/c
1115         mrename $DIR/R16a/b/c $DIR/R16a && error "rename to sub-subdir worked!"
1116         $CHECKSTAT -t dir $DIR/R16a || error "$DIR/R16a missing"
1117         $CHECKSTAT -t dir $DIR/R16a/b/c || error "$DIR/R16a/b/c missing"
1118 }
1119 run_test 24t "mkdir .../R16a/b/c; rename .../R16a/b/c .../R16a ="
1120
1121 test_24u() { # bug12192
1122         $MULTIOP $DIR/$tfile C2w$((2048 * 1024))c || error "multiop failed"
1123         $CHECKSTAT -s $((2048 * 1024)) $DIR/$tfile || error "wrong file size"
1124 }
1125 run_test 24u "create stripe file"
1126
1127 simple_cleanup_common() {
1128         local rc=0
1129         trap 0
1130         [ -z "$DIR" ] || [ -z "$tdir" ] && return 0
1131
1132         local start=$SECONDS
1133         rm -rf $DIR/$tdir
1134         rc=$?
1135         wait_delete_completed
1136         echo "cleanup time $((SECONDS - start))"
1137         return $rc
1138 }
1139
1140 max_pages_per_rpc() {
1141         local mdtname="$(printf "MDT%04x" ${1:-0})"
1142         $LCTL get_param -n mdc.*$mdtname*.max_pages_per_rpc
1143 }
1144
1145 test_24v() {
1146         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1147
1148         local nrfiles=${COUNT:-100000}
1149         local fname="$DIR/$tdir/$tfile"
1150
1151         # Performance issue on ZFS see LU-4072 (c.f. LU-2887)
1152         [ "$mds1_FSTYPE" = "zfs" ] && nrfiles=${COUNT:-10000}
1153
1154         test_mkdir "$(dirname $fname)"
1155         # assume MDT0000 has the fewest inodes
1156         local stripes=$($LFS getdirstripe -c $(dirname $fname))
1157         local free_inodes=$(($(mdt_free_inodes 0) * stripes))
1158         [[ $free_inodes -lt $nrfiles ]] && nrfiles=$free_inodes
1159
1160         trap simple_cleanup_common EXIT
1161
1162         createmany -m "$fname" $nrfiles
1163
1164         cancel_lru_locks mdc
1165         lctl set_param mdc.*.stats clear
1166
1167         # was previously test_24D: LU-6101
1168         # readdir() returns correct number of entries after cursor reload
1169         local num_ls=$(ls $DIR/$tdir | wc -l)
1170         local num_uniq=$(ls $DIR/$tdir | sort -u | wc -l)
1171         local num_all=$(ls -a $DIR/$tdir | wc -l)
1172         if [ $num_ls -ne $nrfiles ] || [ $num_uniq -ne $nrfiles ] ||
1173                 [ $num_all -ne $((nrfiles + 2)) ]; then
1174                         error "Expected $nrfiles files, got $num_ls " \
1175                                 "($num_uniq unique $num_all .&..)"
1176         fi
1177         # LU-5 large readdir
1178         # dirent_size = 32 bytes for sizeof(struct lu_dirent) +
1179         #               N bytes for name (len($nrfiles) rounded to 8 bytes) +
1180         #               8 bytes for luda_type (4 bytes rounded to 8 bytes)
1181         # take into account of overhead in lu_dirpage header and end mark in
1182         # each page, plus one in rpc_num calculation.
1183         local dirent_size=$((32 + (${#tfile} | 7) + 1 + 8))
1184         local page_entries=$(((PAGE_SIZE - 24) / dirent_size))
1185         local mdt_idx=$($LFS getdirstripe -i $(dirname $fname))
1186         local rpc_pages=$(max_pages_per_rpc $mdt_idx)
1187         local rpc_max=$((nrfiles / (page_entries * rpc_pages) + stripes))
1188         local mds_readpage=$(calc_stats mdc.*.stats mds_readpage)
1189         echo "readpages: $mds_readpage rpc_max: $rpc_max"
1190         (( $mds_readpage < $rpc_max - 2 || $mds_readpage > $rpc_max + 1)) &&
1191                 error "large readdir doesn't take effect: " \
1192                       "$mds_readpage should be about $rpc_max"
1193
1194         simple_cleanup_common
1195 }
1196 run_test 24v "list large directory (test hash collision, b=17560)"
1197
1198 test_24w() { # bug21506
1199         SZ1=234852
1200         dd if=/dev/zero of=$DIR/$tfile bs=1M count=1 seek=4096 || return 1
1201         dd if=/dev/zero bs=$SZ1 count=1 >> $DIR/$tfile || return 2
1202         dd if=$DIR/$tfile of=$DIR/${tfile}_left bs=1M skip=4097 || return 3
1203         SZ2=`ls -l $DIR/${tfile}_left | awk '{print $5}'`
1204         [[ "$SZ1" -eq "$SZ2" ]] ||
1205                 error "Error reading at the end of the file $tfile"
1206 }
1207 run_test 24w "Reading a file larger than 4Gb"
1208
1209 test_24x() {
1210         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 2 MDTs"
1211         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1212         [[ $MDS1_VERSION -lt $(version_code 2.7.56) ]] &&
1213                 skip "Need MDS version at least 2.7.56"
1214
1215         local MDTIDX=1
1216         local remote_dir=$DIR/$tdir/remote_dir
1217
1218         test_mkdir $DIR/$tdir
1219         $LFS mkdir -i $MDTIDX $remote_dir ||
1220                 error "create remote directory failed"
1221
1222         test_mkdir $DIR/$tdir/src_dir
1223         touch $DIR/$tdir/src_file
1224         test_mkdir $remote_dir/tgt_dir
1225         touch $remote_dir/tgt_file
1226
1227         mrename $DIR/$tdir/src_dir $remote_dir/tgt_dir ||
1228                 error "rename dir cross MDT failed!"
1229
1230         mrename $DIR/$tdir/src_file $remote_dir/tgt_file ||
1231                 error "rename file cross MDT failed!"
1232
1233         touch $DIR/$tdir/ln_file
1234         ln $DIR/$tdir/ln_file $remote_dir/ln_name ||
1235                 error "ln file cross MDT failed"
1236
1237         rm -rf $DIR/$tdir || error "Can not delete directories"
1238 }
1239 run_test 24x "cross MDT rename/link"
1240
1241 test_24y() {
1242         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 2 MDTs"
1243         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1244
1245         local remote_dir=$DIR/$tdir/remote_dir
1246         local mdtidx=1
1247
1248         test_mkdir $DIR/$tdir
1249         $LFS mkdir -i $mdtidx $remote_dir ||
1250                 error "create remote directory failed"
1251
1252         test_mkdir $remote_dir/src_dir
1253         touch $remote_dir/src_file
1254         test_mkdir $remote_dir/tgt_dir
1255         touch $remote_dir/tgt_file
1256
1257         mrename $remote_dir/src_dir $remote_dir/tgt_dir ||
1258                 error "rename subdir in the same remote dir failed!"
1259
1260         mrename $remote_dir/src_file $remote_dir/tgt_file ||
1261                 error "rename files in the same remote dir failed!"
1262
1263         ln $remote_dir/tgt_file $remote_dir/tgt_file1 ||
1264                 error "link files in the same remote dir failed!"
1265
1266         rm -rf $DIR/$tdir || error "Can not delete directories"
1267 }
1268 run_test 24y "rename/link on the same dir should succeed"
1269
1270 test_24z() {
1271         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 2 MDTs"
1272         [[ $MDS1_VERSION -lt $(version_code 2.12.51) ]] &&
1273                 skip "Need MDS version at least 2.12.51"
1274
1275         local index
1276
1277         for index in 0 1; do
1278                 $LFS mkdir -i $index $DIR/$tdir.$index || error "mkdir failed"
1279                 touch $DIR/$tdir.0/$tfile.$index || error "touch failed"
1280         done
1281
1282         mv $DIR/$tdir.0/$tfile.0 $DIR/$tdir.1 || error "mv $tfile.0 failed"
1283
1284         index=$($LFS getstripe -m $DIR/$tdir.1/$tfile.0)
1285         [ $index -eq 0 ] || error "$tfile.0 is on MDT$index"
1286
1287         local mdts=$(comma_list $(mdts_nodes))
1288
1289         do_nodes $mdts $LCTL set_param mdt.*.enable_remote_rename=0
1290         stack_trap "do_nodes $mdts $LCTL \
1291                 set_param mdt.*.enable_remote_rename=1" EXIT
1292
1293         mv $DIR/$tdir.0/$tfile.1 $DIR/$tdir.1 || error "mv $tfile.1 failed"
1294
1295         index=$($LFS getstripe -m $DIR/$tdir.1/$tfile.1)
1296         [ $index -eq 1 ] || error "$tfile.1 is on MDT$index"
1297 }
1298 run_test 24z "cross-MDT rename is done as cp"
1299
1300 test_24A() { # LU-3182
1301         local NFILES=5000
1302
1303         rm -rf $DIR/$tdir
1304         test_mkdir $DIR/$tdir
1305         trap simple_cleanup_common EXIT
1306         createmany -m $DIR/$tdir/$tfile $NFILES
1307         local t=$(ls $DIR/$tdir | wc -l)
1308         local u=$(ls $DIR/$tdir | sort -u | wc -l)
1309         local v=$(ls -ai $DIR/$tdir | sort -u | wc -l)
1310         if [ $t -ne $NFILES ] || [ $u -ne $NFILES ] ||
1311            [ $v -ne $((NFILES + 2)) ] ; then
1312                 error "Expected $NFILES files, got $t ($u unique $v .&..)"
1313         fi
1314
1315         simple_cleanup_common || error "Can not delete directories"
1316 }
1317 run_test 24A "readdir() returns correct number of entries."
1318
1319 test_24B() { # LU-4805
1320         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
1321
1322         local count
1323
1324         test_mkdir $DIR/$tdir
1325         $LFS setdirstripe -i0 -c$MDSCOUNT $DIR/$tdir/striped_dir ||
1326                 error "create striped dir failed"
1327
1328         count=$(ls -ai $DIR/$tdir/striped_dir | wc -l)
1329         [ $count -eq 2 ] || error "Expected 2, got $count"
1330
1331         touch $DIR/$tdir/striped_dir/a
1332
1333         count=$(ls -ai $DIR/$tdir/striped_dir | wc -l)
1334         [ $count -eq 3 ] || error "Expected 3, got $count"
1335
1336         touch $DIR/$tdir/striped_dir/.f
1337
1338         count=$(ls -ai $DIR/$tdir/striped_dir | wc -l)
1339         [ $count -eq 4 ] || error "Expected 4, got $count"
1340
1341         rm -rf $DIR/$tdir || error "Can not delete directories"
1342 }
1343 run_test 24B "readdir for striped dir return correct number of entries"
1344
1345 test_24C() {
1346         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
1347
1348         mkdir $DIR/$tdir
1349         mkdir $DIR/$tdir/d0
1350         mkdir $DIR/$tdir/d1
1351
1352         $LFS setdirstripe -i0 -c$MDSCOUNT $DIR/$tdir/d0/striped_dir ||
1353                 error "create striped dir failed"
1354
1355         cd $DIR/$tdir/d0/striped_dir
1356
1357         local d0_ino=$(ls -i -l -a $DIR/$tdir | grep "d0" | awk '{print $1}')
1358         local d1_ino=$(ls -i -l -a $DIR/$tdir | grep "d1" | awk '{print $1}')
1359         local parent_ino=$(ls -i -l -a | grep "\.\." | awk '{print $1}')
1360
1361         [ "$d0_ino" = "$parent_ino" ] ||
1362                 error ".. wrong, expect $d0_ino, get $parent_ino"
1363
1364         mv $DIR/$tdir/d0/striped_dir $DIR/$tdir/d1/ ||
1365                 error "mv striped dir failed"
1366
1367         parent_ino=$(ls -i -l -a | grep "\.\." | awk '{print $1}')
1368
1369         [ "$d1_ino" = "$parent_ino" ] ||
1370                 error ".. wrong after mv, expect $d1_ino, get $parent_ino"
1371 }
1372 run_test 24C "check .. in striped dir"
1373
1374 test_24E() {
1375         [[ $MDSCOUNT -lt 4 ]] && skip_env "needs >= 4 MDTs"
1376         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1377
1378         mkdir -p $DIR/$tdir
1379         mkdir $DIR/$tdir/src_dir
1380         $LFS mkdir -i 1 $DIR/$tdir/src_dir/src_child ||
1381                 error "create remote source failed"
1382
1383         touch $DIR/$tdir/src_dir/src_child/a
1384
1385         $LFS mkdir -i 2 $DIR/$tdir/tgt_dir ||
1386                 error "create remote target dir failed"
1387
1388         $LFS mkdir -i 3 $DIR/$tdir/tgt_dir/tgt_child ||
1389                 error "create remote target child failed"
1390
1391         mrename $DIR/$tdir/src_dir/src_child $DIR/$tdir/tgt_dir/tgt_child ||
1392                 error "rename dir cross MDT failed!"
1393
1394         find $DIR/$tdir
1395
1396         $CHECKSTAT -t dir $DIR/$tdir/src_dir/src_child &&
1397                 error "src_child still exists after rename"
1398
1399         $CHECKSTAT -t file $DIR/$tdir/tgt_dir/tgt_child/a ||
1400                 error "missing file(a) after rename"
1401
1402         rm -rf $DIR/$tdir || error "Can not delete directories"
1403 }
1404 run_test 24E "cross MDT rename/link"
1405
1406 test_24F () {
1407         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs" && return 0
1408
1409         local repeats=1000
1410         [ "$SLOW" = "no" ] && repeats=100
1411
1412         mkdir -p $DIR/$tdir
1413
1414         echo "$repeats repeats"
1415         for ((i = 0; i < repeats; i++)); do
1416                 $LFS mkdir -i0 -c2 $DIR/$tdir/test || error "mkdir fails"
1417                 touch $DIR/$tdir/test/a || error "touch fails"
1418                 mkdir $DIR/$tdir/test/b || error "mkdir fails"
1419                 rm -rf $DIR/$tdir/test || error "rmdir fails"
1420         done
1421
1422         true
1423 }
1424 run_test 24F "hash order vs readdir (LU-11330)"
1425
1426 test_25a() {
1427         echo '== symlink sanity ============================================='
1428
1429         test_mkdir $DIR/d25
1430         ln -s d25 $DIR/s25
1431         touch $DIR/s25/foo ||
1432                 error "File creation in symlinked directory failed"
1433 }
1434 run_test 25a "create file in symlinked directory ==============="
1435
1436 test_25b() {
1437         [ ! -d $DIR/d25 ] && test_25a
1438         $CHECKSTAT -t file $DIR/s25/foo || error "$DIR/s25/foo not file type"
1439 }
1440 run_test 25b "lookup file in symlinked directory ==============="
1441
1442 test_26a() {
1443         test_mkdir $DIR/d26
1444         test_mkdir $DIR/d26/d26-2
1445         ln -s d26/d26-2 $DIR/s26
1446         touch $DIR/s26/foo || error "File creation failed"
1447 }
1448 run_test 26a "multiple component symlink ======================="
1449
1450 test_26b() {
1451         test_mkdir -p $DIR/$tdir/d26-2
1452         ln -s $tdir/d26-2/foo $DIR/s26-2
1453         touch $DIR/s26-2 || error "File creation failed"
1454 }
1455 run_test 26b "multiple component symlink at end of lookup ======"
1456
1457 test_26c() {
1458         test_mkdir $DIR/d26.2
1459         touch $DIR/d26.2/foo
1460         ln -s d26.2 $DIR/s26.2-1
1461         ln -s s26.2-1 $DIR/s26.2-2
1462         ln -s s26.2-2 $DIR/s26.2-3
1463         chmod 0666 $DIR/s26.2-3/foo
1464 }
1465 run_test 26c "chain of symlinks"
1466
1467 # recursive symlinks (bug 439)
1468 test_26d() {
1469         ln -s d26-3/foo $DIR/d26-3
1470 }
1471 run_test 26d "create multiple component recursive symlink"
1472
1473 test_26e() {
1474         [ ! -h $DIR/d26-3 ] && test_26d
1475         rm $DIR/d26-3
1476 }
1477 run_test 26e "unlink multiple component recursive symlink"
1478
1479 # recursive symlinks (bug 7022)
1480 test_26f() {
1481         test_mkdir $DIR/$tdir
1482         test_mkdir $DIR/$tdir/$tfile
1483         cd $DIR/$tdir/$tfile           || error "cd $DIR/$tdir/$tfile failed"
1484         test_mkdir -p lndir/bar1
1485         test_mkdir $DIR/$tdir/$tfile/$tfile
1486         cd $tfile                || error "cd $tfile failed"
1487         ln -s .. dotdot          || error "ln dotdot failed"
1488         ln -s dotdot/lndir lndir || error "ln lndir failed"
1489         cd $DIR/$tdir                 || error "cd $DIR/$tdir failed"
1490         output=`ls $tfile/$tfile/lndir/bar1`
1491         [ "$output" = bar1 ] && error "unexpected output"
1492         rm -r $tfile             || error "rm $tfile failed"
1493         $CHECKSTAT -a $DIR/$tfile || error "$tfile not gone"
1494 }
1495 run_test 26f "rm -r of a directory which has recursive symlink"
1496
1497 test_27a() {
1498         test_mkdir $DIR/$tdir
1499         $LFS getstripe $DIR/$tdir
1500         $LFS setstripe -c 1 $DIR/$tdir/$tfile || error "setstripe failed"
1501         $CHECKSTAT -t file $DIR/$tdir/$tfile || error "checkstat failed"
1502         cp /etc/hosts $DIR/$tdir/$tfile || error "Can't copy to one stripe file"
1503 }
1504 run_test 27a "one stripe file"
1505
1506 test_27b() {
1507         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
1508
1509         test_mkdir $DIR/$tdir
1510         $LFS setstripe -c 2 $DIR/$tdir/$tfile || error "setstripe failed"
1511         $LFS getstripe -c $DIR/$tdir/$tfile
1512         [ $($LFS getstripe -c $DIR/$tdir/$tfile) -eq 2 ] ||
1513                 error "two-stripe file doesn't have two stripes"
1514
1515         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=4k count=4 || error "dd failed"
1516 }
1517 run_test 27b "create and write to two stripe file"
1518
1519 # 27c family tests specific striping, setstripe -o
1520 test_27ca() {
1521         [[ $OSTCOUNT -lt 2 ]] && skip_env "skipping 2-stripe test"
1522         test_mkdir -p $DIR/$tdir
1523         local osts="1"
1524
1525         $LFS setstripe -o $osts $DIR/$tdir/$tfile  || error "setstripe failed"
1526         $LFS getstripe -i $DIR/$tdir/$tfile
1527         [ $($LFS getstripe -i $DIR/$tdir/$tfile ) -eq $osts ] ||
1528                 error "stripe not on specified OST"
1529
1530         dd if=/dev/zero of=$DIR/$tdir/$tfile  bs=1M count=4 || error "dd failed"
1531 }
1532 run_test 27ca "one stripe on specified OST"
1533
1534 test_27cb() {
1535         [[ $OSTCOUNT -lt 2 ]] && skip_env "skipping 2-stripe test"
1536         test_mkdir -p $DIR/$tdir
1537         local osts="1,0"
1538         $LFS setstripe -o $osts $DIR/$tdir/$tfile || error "setstripe failed"
1539         local getstripe=$($LFS getstripe $DIR/$tdir/$tfile)
1540         echo "$getstripe"
1541
1542         # Strip getstripe output to a space separated list of OSTs
1543         local getstripe_osts=$(echo "$getstripe" | sed -e '1,/obdidx/d' |\
1544                 awk '{print $1}' | tr '\n' '\ ' | sed -e 's/[[:space:]]*$//')
1545         [ "$getstripe_osts" = "${osts//,/ }" ] ||
1546                 error "stripes not on specified OSTs"
1547
1548         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=4 || error "dd failed"
1549 }
1550 run_test 27cb "two stripes on specified OSTs"
1551
1552 test_27cc() {
1553         [[ $OSTCOUNT -lt 2 ]] && skip_env "skipping 2-stripe test"
1554         [[ $($LCTL get_param mdc.*.import) =~ connect_flags.*overstriping ]] ||
1555                 skip "server does not support overstriping"
1556
1557         test_mkdir -p $DIR/$tdir
1558         local osts="0,0"
1559         $LFS setstripe -o $osts $DIR/$tdir/$tfile || error "setstripe failed"
1560         local getstripe=$($LFS getstripe $DIR/$tdir/$tfile)
1561         echo "$getstripe"
1562
1563         # Strip getstripe output to a space separated list of OSTs
1564         local getstripe_osts=$(echo "$getstripe" | sed -e '1,/obdidx/d' |\
1565                 awk '{print $1}' | tr '\n' '\ ' | sed -e 's/[[:space:]]*$//')
1566         [ "$getstripe_osts" = "${osts//,/ }" ] ||
1567                 error "stripes not on specified OSTs"
1568
1569         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=4 || error "dd failed"
1570 }
1571 run_test 27cc "two stripes on the same OST"
1572
1573 test_27cd() {
1574         [[ $OSTCOUNT -lt 2 ]] && skip_env "skipping 2-stripe test"
1575         [[ $($LCTL get_param mdc.*.import) =~ connect_flags.*overstriping ]] ||
1576                 skip "server does not support overstriping"
1577         test_mkdir -p $DIR/$tdir
1578         local osts="0,1,1,0"
1579         $LFS setstripe -o $osts $DIR/$tdir/$tfile || error "setstripe failed"
1580         local getstripe=$($LFS getstripe $DIR/$tdir/$tfile)
1581         echo "$getstripe"
1582
1583         # Strip getstripe output to a space separated list of OSTs
1584         local getstripe_osts=$(echo "$getstripe" | sed -e '1,/obdidx/d' |\
1585                 awk '{print $1}' | tr '\n' '\ ' | sed -e 's/[[:space:]]*$//')
1586         [ "$getstripe_osts" = "${osts//,/ }" ] ||
1587                 error "stripes not on specified OSTs"
1588
1589         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=4 || error "dd failed"
1590 }
1591 run_test 27cd "four stripes on two OSTs"
1592
1593 test_27ce() {
1594         [[ $OSTCOUNT -ge $(($LOV_MAX_STRIPE_COUNT / 2)) ]] &&
1595                 skip_env "too many osts, skipping"
1596         [[ $($LCTL get_param mdc.*.import) =~ connect_flags.*overstriping ]] ||
1597                 skip "server does not support overstriping"
1598         # We do one more stripe than we have OSTs
1599         [ $OSTCOUNT -ge 159 ] || large_xattr_enabled ||
1600                 skip_env "ea_inode feature disabled"
1601
1602         test_mkdir -p $DIR/$tdir
1603         local osts=""
1604         for i in $(seq 0 $OSTCOUNT);
1605         do
1606                 osts=$osts"0"
1607                 if [ $i -ne $OSTCOUNT ]; then
1608                         osts=$osts","
1609                 fi
1610         done
1611         $LFS setstripe -o $osts $DIR/$tdir/$tfile || error "setstripe failed"
1612         local getstripe=$($LFS getstripe $DIR/$tdir/$tfile)
1613         echo "$getstripe"
1614
1615         # Strip getstripe output to a space separated list of OSTs
1616         local getstripe_osts=$(echo "$getstripe" | sed -e '1,/obdidx/d' |\
1617                 awk '{print $1}' | tr '\n' '\ ' | sed -e 's/[[:space:]]*$//')
1618         [ "$getstripe_osts" = "${osts//,/ }" ] ||
1619                 error "stripes not on specified OSTs"
1620
1621         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=4 || error "dd failed"
1622 }
1623 run_test 27ce "more stripes than OSTs with -o"
1624
1625 test_27d() {
1626         test_mkdir $DIR/$tdir
1627         $LFS setstripe -c 0 -i -1 -S 0 $DIR/$tdir/$tfile ||
1628                 error "setstripe failed"
1629         $CHECKSTAT -t file $DIR/$tdir/$tfile || error "checkstat failed"
1630         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=4k count=4 || error "dd failed"
1631 }
1632 run_test 27d "create file with default settings"
1633
1634 test_27e() {
1635         # LU-5839 adds check for existed layout before setting it
1636         [[ $MDS1_VERSION -lt $(version_code 2.7.56) ]] &&
1637                 skip "Need MDS version at least 2.7.56"
1638
1639         test_mkdir $DIR/$tdir
1640         $LFS setstripe -c 2 $DIR/$tdir/$tfile || error "setstripe failed"
1641         $LFS setstripe -c 2 $DIR/$tdir/$tfile && error "setstripe worked twice"
1642         $CHECKSTAT -t file $DIR/$tdir/$tfile || error "checkstat failed"
1643 }
1644 run_test 27e "setstripe existing file (should return error)"
1645
1646 test_27f() {
1647         test_mkdir $DIR/$tdir
1648         $LFS setstripe -S 100 -i 0 -c 1 $DIR/$tdir/$tfile &&
1649                 error "$LFS setstripe $DIR/$tdir/$tfile failed"
1650         $CHECKSTAT -t file $DIR/$tdir/$tfile &&
1651                 error "$CHECKSTAT -t file $DIR/$tdir/$tfile should fail"
1652         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=4k count=4 || error "dd failed"
1653         $LFS getstripe $DIR/$tdir/$tfile || error "$LFS getstripe failed"
1654 }
1655 run_test 27f "setstripe with bad stripe size (should return error)"
1656
1657 test_27g() {
1658         test_mkdir $DIR/$tdir
1659         $MCREATE $DIR/$tdir/$tfile || error "mcreate failed"
1660         $LFS getstripe $DIR/$tdir/$tfile 2>&1 | grep "no stripe info" ||
1661                 error "$DIR/$tdir/$tfile has object"
1662 }
1663 run_test 27g "$LFS getstripe with no objects"
1664
1665 test_27ga() {
1666         test_mkdir $DIR/$tdir
1667         touch $DIR/$tdir/$tfile || error "touch failed"
1668         ln -s bogus $DIR/$tdir/$tfile.2 || error "ln failed"
1669         $LFS getstripe -m $DIR/$tdir/$tfile $DIR/$tdir/$tfile.2
1670         local rc=$?
1671         (( rc == 2 )) || error "getstripe did not return ENOENT"
1672 }
1673 run_test 27ga "$LFS getstripe with missing file (should return error)"
1674
1675 test_27i() {
1676         test_mkdir $DIR/$tdir
1677         touch $DIR/$tdir/$tfile || error "touch failed"
1678         [[ $($LFS getstripe -c $DIR/$tdir/$tfile) -gt 0 ]] ||
1679                 error "missing objects"
1680 }
1681 run_test 27i "$LFS getstripe with some objects"
1682
1683 test_27j() {
1684         test_mkdir $DIR/$tdir
1685         $LFS setstripe -i $OSTCOUNT $DIR/$tdir/$tfile &&
1686                 error "setstripe failed" || true
1687 }
1688 run_test 27j "setstripe with bad stripe offset (should return error)"
1689
1690 test_27k() { # bug 2844
1691         test_mkdir $DIR/$tdir
1692         local file=$DIR/$tdir/$tfile
1693         local ll_max_blksize=$((4 * 1024 * 1024))
1694         $LFS setstripe -S 67108864 $file || error "setstripe failed"
1695         local blksize=$(stat $file | awk '/IO Block:/ { print $7 }')
1696         [ $blksize -le $ll_max_blksize ] || error "1:$blksize > $ll_max_blksize"
1697         dd if=/dev/zero of=$file bs=4k count=1
1698         blksize=$(stat $file | awk '/IO Block:/ { print $7 }')
1699         [ $blksize -le $ll_max_blksize ] || error "2:$blksize > $ll_max_blksize"
1700 }
1701 run_test 27k "limit i_blksize for broken user apps"
1702
1703 test_27l() {
1704         mcreate $DIR/$tfile || error "creating file"
1705         $RUNAS $LFS setstripe -c 1 $DIR/$tfile &&
1706                 error "setstripe should have failed" || true
1707 }
1708 run_test 27l "check setstripe permissions (should return error)"
1709
1710 test_27m() {
1711         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
1712
1713         [ -n "$RCLIENTS" -o -n "$MOUNT_2" ] &&
1714                 skip_env "multiple clients -- skipping"
1715
1716         ORIGFREE=$($LCTL get_param -n lov.$FSNAME-clilov-*.kbytesavail |
1717                    head -n1)
1718         if [[ $ORIGFREE -gt $MAXFREE ]]; then
1719                 skip "$ORIGFREE > $MAXFREE skipping out-of-space test on OST0"
1720         fi
1721         trap simple_cleanup_common EXIT
1722         test_mkdir $DIR/$tdir
1723         $LFS setstripe -i 0 -c 1 $DIR/$tdir/$tfile.1
1724         dd if=/dev/zero of=$DIR/$tdir/$tfile.1 bs=1024 count=$MAXFREE &&
1725                 error "dd should fill OST0"
1726         i=2
1727         while $LFS setstripe -i 0 -c 1 $DIR/$tdir/$tfile.$i; do
1728                 i=$((i + 1))
1729                 [ $i -gt 256 ] && break
1730         done
1731         i=$((i + 1))
1732         touch $DIR/$tdir/$tfile.$i
1733         [ $($LFS getstripe $DIR/$tdir/$tfile.$i | grep -A 10 obdidx |
1734             awk '{print $1}'| grep -w "0") ] &&
1735                 error "OST0 was full but new created file still use it"
1736         i=$((i + 1))
1737         touch $DIR/$tdir/$tfile.$i
1738         [ $($LFS getstripe $DIR/$tdir/$tfile.$i | grep -A 10 obdidx |
1739             awk '{print $1}'| grep -w "0") ] &&
1740                 error "OST0 was full but new created file still use it"
1741         simple_cleanup_common
1742 }
1743 run_test 27m "create file while OST0 was full"
1744
1745 # OSCs keep a NOSPC flag that will be reset after ~5s (qos_maxage)
1746 # if the OST isn't full anymore.
1747 reset_enospc() {
1748         local OSTIDX=${1:-""}
1749
1750         local list=$(comma_list $(osts_nodes))
1751         [ "$OSTIDX" ] && list=$(facet_host ost$((OSTIDX + 1)))
1752
1753         do_nodes $list lctl set_param fail_loc=0
1754         sync    # initiate all OST_DESTROYs from MDS to OST
1755         sleep_maxage
1756 }
1757
1758 exhaust_precreations() {
1759         local OSTIDX=$1
1760         local FAILLOC=$2
1761         local FAILIDX=${3:-$OSTIDX}
1762         local ofacet=ost$((OSTIDX + 1))
1763
1764         test_mkdir -p -c1 $DIR/$tdir
1765         local mdtidx=$($LFS getstripe -m $DIR/$tdir)
1766         local mfacet=mds$((mdtidx + 1))
1767         echo OSTIDX=$OSTIDX MDTIDX=$mdtidx
1768
1769         local OST=$(ostname_from_index $OSTIDX)
1770
1771         # on the mdt's osc
1772         local mdtosc_proc1=$(get_mdtosc_proc_path $mfacet $OST)
1773         local last_id=$(do_facet $mfacet lctl get_param -n \
1774                         osp.$mdtosc_proc1.prealloc_last_id)
1775         local next_id=$(do_facet $mfacet lctl get_param -n \
1776                         osp.$mdtosc_proc1.prealloc_next_id)
1777
1778         local mdtosc_proc2=$(get_mdtosc_proc_path $mfacet)
1779         do_facet $mfacet lctl get_param osp.$mdtosc_proc2.prealloc*
1780
1781         test_mkdir -p $DIR/$tdir/${OST}
1782         $LFS setstripe -i $OSTIDX -c 1 $DIR/$tdir/${OST}
1783 #define OBD_FAIL_OST_ENOSPC              0x215
1784         do_facet $ofacet lctl set_param fail_val=$FAILIDX fail_loc=0x215
1785         echo "Creating to objid $last_id on ost $OST..."
1786         createmany -o $DIR/$tdir/${OST}/f $next_id $((last_id - next_id + 2))
1787         do_facet $mfacet lctl get_param osp.$mdtosc_proc2.prealloc*
1788         do_facet $ofacet lctl set_param fail_loc=$FAILLOC
1789         sleep_maxage
1790 }
1791
1792 exhaust_all_precreations() {
1793         local i
1794         for (( i=0; i < OSTCOUNT; i++ )) ; do
1795                 exhaust_precreations $i $1 -1
1796         done
1797 }
1798
1799 test_27n() {
1800         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
1801         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1802         remote_mds_nodsh && skip "remote MDS with nodsh"
1803         remote_ost_nodsh && skip "remote OST with nodsh"
1804
1805         reset_enospc
1806         rm -f $DIR/$tdir/$tfile
1807         exhaust_precreations 0 0x80000215
1808         $LFS setstripe -c -1 $DIR/$tdir || error "setstripe failed"
1809         touch $DIR/$tdir/$tfile || error "touch failed"
1810         $LFS getstripe $DIR/$tdir/$tfile
1811         reset_enospc
1812 }
1813 run_test 27n "create file with some full OSTs"
1814
1815 test_27o() {
1816         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
1817         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1818         remote_mds_nodsh && skip "remote MDS with nodsh"
1819         remote_ost_nodsh && skip "remote OST with nodsh"
1820
1821         reset_enospc
1822         rm -f $DIR/$tdir/$tfile
1823         exhaust_all_precreations 0x215
1824
1825         touch $DIR/$tdir/$tfile && error "able to create $DIR/$tdir/$tfile"
1826
1827         reset_enospc
1828         rm -rf $DIR/$tdir/*
1829 }
1830 run_test 27o "create file with all full OSTs (should error)"
1831
1832 test_27p() {
1833         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
1834         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1835         remote_mds_nodsh && skip "remote MDS with nodsh"
1836         remote_ost_nodsh && skip "remote OST with nodsh"
1837
1838         reset_enospc
1839         rm -f $DIR/$tdir/$tfile
1840         test_mkdir $DIR/$tdir
1841
1842         $MCREATE $DIR/$tdir/$tfile || error "mcreate failed"
1843         $TRUNCATE $DIR/$tdir/$tfile 80000000 || error "truncate failed"
1844         $CHECKSTAT -s 80000000 $DIR/$tdir/$tfile || error "checkstat failed"
1845
1846         exhaust_precreations 0 0x80000215
1847         echo foo >> $DIR/$tdir/$tfile || error "append failed"
1848         $CHECKSTAT -s 80000004 $DIR/$tdir/$tfile || error "checkstat failed"
1849         $LFS getstripe $DIR/$tdir/$tfile
1850
1851         reset_enospc
1852 }
1853 run_test 27p "append to a truncated file with some full OSTs"
1854
1855 test_27q() {
1856         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
1857         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1858         remote_mds_nodsh && skip "remote MDS with nodsh"
1859         remote_ost_nodsh && skip "remote OST with nodsh"
1860
1861         reset_enospc
1862         rm -f $DIR/$tdir/$tfile
1863
1864         test_mkdir $DIR/$tdir
1865         $MCREATE $DIR/$tdir/$tfile || error "mcreate $DIR/$tdir/$tfile failed"
1866         $TRUNCATE $DIR/$tdir/$tfile 80000000 ||
1867                 error "truncate $DIR/$tdir/$tfile failed"
1868         $CHECKSTAT -s 80000000 $DIR/$tdir/$tfile || error "checkstat failed"
1869
1870         exhaust_all_precreations 0x215
1871
1872         echo foo >> $DIR/$tdir/$tfile && error "append succeeded"
1873         $CHECKSTAT -s 80000000 $DIR/$tdir/$tfile || error "checkstat 2 failed"
1874
1875         reset_enospc
1876 }
1877 run_test 27q "append to truncated file with all OSTs full (should error)"
1878
1879 test_27r() {
1880         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
1881         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1882         remote_mds_nodsh && skip "remote MDS with nodsh"
1883         remote_ost_nodsh && skip "remote OST with nodsh"
1884
1885         reset_enospc
1886         rm -f $DIR/$tdir/$tfile
1887         exhaust_precreations 0 0x80000215
1888
1889         $LFS setstripe -i 0 -c 2 $DIR/$tdir/$tfile || error "setstripe failed"
1890
1891         reset_enospc
1892 }
1893 run_test 27r "stripe file with some full OSTs (shouldn't LBUG) ="
1894
1895 test_27s() { # bug 10725
1896         test_mkdir $DIR/$tdir
1897         local stripe_size=$((4096 * 1024 * 1024))       # 2^32
1898         local stripe_count=0
1899         [ $OSTCOUNT -eq 1 ] || stripe_count=2
1900         $LFS setstripe -S $stripe_size -c $stripe_count $DIR/$tdir &&
1901                 error "stripe width >= 2^32 succeeded" || true
1902
1903 }
1904 run_test 27s "lsm_xfersize overflow (should error) (bug 10725)"
1905
1906 test_27t() { # bug 10864
1907         WDIR=$(pwd)
1908         WLFS=$(which lfs)
1909         cd $DIR
1910         touch $tfile
1911         $WLFS getstripe $tfile
1912         cd $WDIR
1913 }
1914 run_test 27t "check that utils parse path correctly"
1915
1916 test_27u() { # bug 4900
1917         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
1918         remote_mds_nodsh && skip "remote MDS with nodsh"
1919
1920         local index
1921         local list=$(comma_list $(mdts_nodes))
1922
1923 #define OBD_FAIL_MDS_OSC_PRECREATE      0x139
1924         do_nodes $list $LCTL set_param fail_loc=0x139
1925         test_mkdir -p $DIR/$tdir
1926         trap simple_cleanup_common EXIT
1927         createmany -o $DIR/$tdir/t- 1000
1928         do_nodes $list $LCTL set_param fail_loc=0
1929
1930         TLOG=$TMP/$tfile.getstripe
1931         $LFS getstripe $DIR/$tdir > $TLOG
1932         OBJS=$(awk -vobj=0 '($1 == 0) { obj += 1 } END { print obj; }' $TLOG)
1933         unlinkmany $DIR/$tdir/t- 1000
1934         trap 0
1935         [[ $OBJS -gt 0 ]] &&
1936                 error "$OBJS objects created on OST-0. See $TLOG" ||
1937                 rm -f $TLOG
1938 }
1939 run_test 27u "skip object creation on OSC w/o objects"
1940
1941 test_27v() { # bug 4900
1942         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
1943         [ $PARALLEL == "yes" ] && skip "skip parallel run"
1944         remote_mds_nodsh && skip "remote MDS with nodsh"
1945         remote_ost_nodsh && skip "remote OST with nodsh"
1946
1947         exhaust_all_precreations 0x215
1948         reset_enospc
1949
1950         $LFS setstripe -c 1 $DIR/$tdir         # 1 stripe / file
1951
1952         touch $DIR/$tdir/$tfile
1953         #define OBD_FAIL_TGT_DELAY_PRECREATE     0x705
1954         # all except ost1
1955         for (( i=1; i < OSTCOUNT; i++ )); do
1956                 do_facet ost$i lctl set_param fail_loc=0x705
1957         done
1958         local START=`date +%s`
1959         createmany -o $DIR/$tdir/$tfile 32
1960
1961         local FINISH=`date +%s`
1962         local TIMEOUT=`lctl get_param -n timeout`
1963         local PROCESS=$((FINISH - START))
1964         [ $PROCESS -ge $((TIMEOUT / 2)) ] && \
1965                error "$FINISH - $START >= $TIMEOUT / 2"
1966         sleep $((TIMEOUT / 2 - PROCESS))
1967         reset_enospc
1968 }
1969 run_test 27v "skip object creation on slow OST"
1970
1971 test_27w() { # bug 10997
1972         test_mkdir $DIR/$tdir
1973         $LFS setstripe -S 65536 $DIR/$tdir/f0 || error "setstripe failed"
1974         [ $($LFS getstripe -S $DIR/$tdir/f0) -ne 65536 ] &&
1975                 error "stripe size $size != 65536" || true
1976         [ $($LFS getstripe -d $DIR/$tdir | grep -c "stripe_count") -eq 0 ] &&
1977                 error "$LFS getstripe -d $DIR/$tdir no 'stripe_count'" || true
1978 }
1979 run_test 27w "check $LFS setstripe -S and getstrip -d options"
1980
1981 test_27wa() {
1982         [[ $OSTCOUNT -lt 2 ]] &&
1983                 skip_env "skipping multiple stripe count/offset test"
1984
1985         test_mkdir $DIR/$tdir
1986         for i in $(seq 1 $OSTCOUNT); do
1987                 offset=$((i - 1))
1988                 $LFS setstripe -c $i -i $offset $DIR/$tdir/f$i ||
1989                         error "setstripe -c $i -i $offset failed"
1990                 count=$($LFS getstripe -c $DIR/$tdir/f$i)
1991                 index=$($LFS getstripe -i $DIR/$tdir/f$i)
1992                 [ $count -ne $i ] && error "stripe count $count != $i" || true
1993                 [ $index -ne $offset ] &&
1994                         error "stripe offset $index != $offset" || true
1995         done
1996 }
1997 run_test 27wa "check $LFS setstripe -c -i options"
1998
1999 test_27x() {
2000         remote_ost_nodsh && skip "remote OST with nodsh"
2001         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
2002         [ $PARALLEL == "yes" ] && skip "skip parallel run"
2003
2004         OFFSET=$(($OSTCOUNT - 1))
2005         OSTIDX=0
2006         local OST=$(ostname_from_index $OSTIDX)
2007
2008         test_mkdir $DIR/$tdir
2009         $LFS setstripe -c 1 $DIR/$tdir  # 1 stripe per file
2010         do_facet ost$((OSTIDX + 1)) lctl set_param -n obdfilter.$OST.degraded 1
2011         sleep_maxage
2012         createmany -o $DIR/$tdir/$tfile $OSTCOUNT
2013         for i in $(seq 0 $OFFSET); do
2014                 [ $($LFS getstripe $DIR/$tdir/$tfile$i | grep -A 10 obdidx |
2015                         awk '{print $1}' | grep -w "$OSTIDX") ] &&
2016                 error "OST0 was degraded but new created file still use it"
2017         done
2018         do_facet ost$((OSTIDX + 1)) lctl set_param -n obdfilter.$OST.degraded 0
2019 }
2020 run_test 27x "create files while OST0 is degraded"
2021
2022 test_27y() {
2023         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
2024         remote_mds_nodsh && skip "remote MDS with nodsh"
2025         remote_ost_nodsh && skip "remote OST with nodsh"
2026         [ $PARALLEL == "yes" ] && skip "skip parallel run"
2027
2028         local mdtosc=$(get_mdtosc_proc_path $SINGLEMDS $FSNAME-OST0000)
2029         local last_id=$(do_facet $SINGLEMDS lctl get_param -n \
2030                 osp.$mdtosc.prealloc_last_id)
2031         local next_id=$(do_facet $SINGLEMDS lctl get_param -n \
2032                 osp.$mdtosc.prealloc_next_id)
2033         local fcount=$((last_id - next_id))
2034         [[ $fcount -eq 0 ]] && skip "not enough space on OST0"
2035         [[ $fcount -gt $OSTCOUNT ]] && fcount=$OSTCOUNT
2036
2037         local MDS_OSCS=$(do_facet $SINGLEMDS lctl dl |
2038                          awk '/[oO][sS][cC].*md[ts]/ { print $4 }')
2039         local OST_DEACTIVE_IDX=-1
2040         local OSC
2041         local OSTIDX
2042         local OST
2043
2044         for OSC in $MDS_OSCS; do
2045                 OST=$(osc_to_ost $OSC)
2046                 OSTIDX=$(index_from_ostuuid $OST)
2047                 if [ $OST_DEACTIVE_IDX == -1 ]; then
2048                         OST_DEACTIVE_IDX=$OSTIDX
2049                 fi
2050                 if [ $OSTIDX != $OST_DEACTIVE_IDX ]; then
2051                         echo $OSC "is Deactivated:"
2052                         do_facet $SINGLEMDS lctl --device  %$OSC deactivate
2053                 fi
2054         done
2055
2056         OSTIDX=$(index_from_ostuuid $OST)
2057         test_mkdir $DIR/$tdir
2058         $LFS setstripe -c 1 $DIR/$tdir      # 1 stripe / file
2059
2060         for OSC in $MDS_OSCS; do
2061                 OST=$(osc_to_ost $OSC)
2062                 OSTIDX=$(index_from_ostuuid $OST)
2063                 if [ $OSTIDX == $OST_DEACTIVE_IDX ]; then
2064                         echo $OST "is degraded:"
2065                         do_facet ost$((OSTIDX+1)) lctl set_param -n \
2066                                                 obdfilter.$OST.degraded=1
2067                 fi
2068         done
2069
2070         sleep_maxage
2071         createmany -o $DIR/$tdir/$tfile $fcount
2072
2073         for OSC in $MDS_OSCS; do
2074                 OST=$(osc_to_ost $OSC)
2075                 OSTIDX=$(index_from_ostuuid $OST)
2076                 if [ $OSTIDX == $OST_DEACTIVE_IDX ]; then
2077                         echo $OST "is recovered from degraded:"
2078                         do_facet ost$((OSTIDX+1)) lctl set_param -n \
2079                                                 obdfilter.$OST.degraded=0
2080                 else
2081                         do_facet $SINGLEMDS lctl --device %$OSC activate
2082                 fi
2083         done
2084
2085         # all osp devices get activated, hence -1 stripe count restored
2086         local stripe_count=0
2087
2088         # sleep 2*lod_qos_maxage seconds waiting for lod qos to notice osp
2089         # devices get activated.
2090         sleep_maxage
2091         $LFS setstripe -c -1 $DIR/$tfile
2092         stripe_count=$($LFS getstripe -c $DIR/$tfile)
2093         rm -f $DIR/$tfile
2094         [ $stripe_count -ne $OSTCOUNT ] &&
2095                 error "Of $OSTCOUNT OSTs, only $stripe_count is available"
2096         return 0
2097 }
2098 run_test 27y "create files while OST0 is degraded and the rest inactive"
2099
2100 check_seq_oid()
2101 {
2102         log "check file $1"
2103
2104         lmm_count=$($LFS getstripe -c $1)
2105         lmm_seq=$($LFS getstripe -v $1 | awk '/lmm_seq/ { print $2 }')
2106         lmm_oid=$($LFS getstripe -v $1 | awk '/lmm_object_id/ { print $2 }')
2107
2108         local old_ifs="$IFS"
2109         IFS=$'[:]'
2110         fid=($($LFS path2fid $1))
2111         IFS="$old_ifs"
2112
2113         log "FID seq ${fid[1]}, oid ${fid[2]} ver ${fid[3]}"
2114         log "LOV seq $lmm_seq, oid $lmm_oid, count: $lmm_count"
2115
2116         # compare lmm_seq and lu_fid->f_seq
2117         [ $lmm_seq = ${fid[1]} ] || { error "SEQ mismatch"; return 1; }
2118         # compare lmm_object_id and lu_fid->oid
2119         [ $lmm_oid = ${fid[2]} ] || { error "OID mismatch"; return 2; }
2120
2121         # check the trusted.fid attribute of the OST objects of the file
2122         local have_obdidx=false
2123         local stripe_nr=0
2124         $LFS getstripe $1 | while read obdidx oid hex seq; do
2125                 # skip lines up to and including "obdidx"
2126                 [ -z "$obdidx" ] && break
2127                 [ "$obdidx" = "obdidx" ] && have_obdidx=true && continue
2128                 $have_obdidx || continue
2129
2130                 local ost=$((obdidx + 1))
2131                 local dev=$(ostdevname $ost)
2132                 local oid_hex
2133
2134                 log "want: stripe:$stripe_nr ost:$obdidx oid:$oid/$hex seq:$seq"
2135
2136                 seq=$(echo $seq | sed -e "s/^0x//g")
2137                 if [ $seq == 0 ] || [ $(facet_fstype ost$ost) == zfs ]; then
2138                         oid_hex=$(echo $oid)
2139                 else
2140                         oid_hex=$(echo $hex | sed -e "s/^0x//g")
2141                 fi
2142                 local obj_file="O/$seq/d$((oid %32))/$oid_hex"
2143
2144                 local ff=""
2145                 #
2146                 # Don't unmount/remount the OSTs if we don't need to do that.
2147                 # LU-2577 changes filter_fid to be smaller, so debugfs needs
2148                 # update too, until that use mount/ll_decode_filter_fid/mount.
2149                 # Re-enable when debugfs will understand new filter_fid.
2150                 #
2151                 if [ $(facet_fstype ost$ost) == ldiskfs ]; then
2152                         ff=$(do_facet ost$ost "$DEBUGFS -c -R 'stat $obj_file' \
2153                                 $dev 2>/dev/null" | grep "parent=")
2154                 fi
2155                 if [ -z "$ff" ]; then
2156                         stop ost$ost
2157                         mount_fstype ost$ost
2158                         ff=$(do_facet ost$ost $LL_DECODE_FILTER_FID \
2159                                 $(facet_mntpt ost$ost)/$obj_file)
2160                         unmount_fstype ost$ost
2161                         start ost$ost $dev $OST_MOUNT_OPTS
2162                         clients_up
2163                 fi
2164
2165                 [ -z "$ff" ] && error "$obj_file: no filter_fid info"
2166
2167                 echo "$ff" | sed -e 's#.*objid=#got: objid=#'
2168
2169                 # /mnt/O/0/d23/23: objid=23 seq=0 parent=[0x200000400:0x1e:0x1]
2170                 # fid: objid=23 seq=0 parent=[0x200000400:0x1e:0x0] stripe=1
2171                 #
2172                 # fid: parent=[0x200000400:0x1e:0x0] stripe=1 stripe_count=2 \
2173                 #       stripe_size=1048576 component_id=1 component_start=0 \
2174                 #       component_end=33554432
2175                 local ff_parent=$(sed -e 's/.*parent=.//' <<<$ff)
2176                 local ff_pseq=$(cut -d: -f1 <<<$ff_parent)
2177                 local ff_poid=$(cut -d: -f2 <<<$ff_parent)
2178                 local ff_pstripe
2179                 if grep -q 'stripe=' <<<$ff; then
2180                         ff_pstripe=$(sed -e 's/.*stripe=//' -e 's/ .*//' <<<$ff)
2181                 else
2182                         # $LL_DECODE_FILTER_FID does not print "stripe="; look
2183                         # into f_ver in this case.  See comment on ff_parent.
2184                         ff_pstripe=$(cut -d: -f3 <<<$ff_parent | sed -e 's/]//')
2185                 fi
2186
2187                 # compare lmm_seq and filter_fid->ff_parent.f_seq
2188                 [ $ff_pseq = $lmm_seq ] ||
2189                         error "FF parent SEQ $ff_pseq != $lmm_seq"
2190                 # compare lmm_object_id and filter_fid->ff_parent.f_oid
2191                 [ $ff_poid = $lmm_oid ] ||
2192                         error "FF parent OID $ff_poid != $lmm_oid"
2193                 (($ff_pstripe == $stripe_nr)) ||
2194                         error "FF stripe $ff_pstripe != $stripe_nr"
2195
2196                 stripe_nr=$((stripe_nr + 1))
2197                 [ $CLIENT_VERSION -lt $(version_code 2.9.55) ] &&
2198                         continue
2199                 if grep -q 'stripe_count=' <<<$ff; then
2200                         local ff_scnt=$(sed -e 's/.*stripe_count=//' \
2201                                             -e 's/ .*//' <<<$ff)
2202                         [ $lmm_count = $ff_scnt ] ||
2203                                 error "FF stripe count $lmm_count != $ff_scnt"
2204                 fi
2205         done
2206 }
2207
2208 test_27z() {
2209         [ $PARALLEL == "yes" ] && skip "skip parallel run"
2210         remote_ost_nodsh && skip "remote OST with nodsh"
2211
2212         test_mkdir $DIR/$tdir
2213         $LFS setstripe -c 1 -i 0 -S 64k $DIR/$tdir/$tfile-1 ||
2214                 { error "setstripe -c -1 failed"; return 1; }
2215         # We need to send a write to every object to get parent FID info set.
2216         # This _should_ also work for setattr, but does not currently.
2217         # touch $DIR/$tdir/$tfile-1 ||
2218         dd if=/dev/zero of=$DIR/$tdir/$tfile-1 bs=1M count=1 ||
2219                 { error "dd $tfile-1 failed"; return 2; }
2220         $LFS setstripe -c -1 -i $((OSTCOUNT - 1)) -S 1M $DIR/$tdir/$tfile-2 ||
2221                 { error "setstripe -c -1 failed"; return 3; }
2222         dd if=/dev/zero of=$DIR/$tdir/$tfile-2 bs=1M count=$OSTCOUNT ||
2223                 { error "dd $tfile-2 failed"; return 4; }
2224
2225         # make sure write RPCs have been sent to OSTs
2226         sync; sleep 5; sync
2227
2228         check_seq_oid $DIR/$tdir/$tfile-1 || return 5
2229         check_seq_oid $DIR/$tdir/$tfile-2 || return 6
2230 }
2231 run_test 27z "check SEQ/OID on the MDT and OST filesystems"
2232
2233 test_27A() { # b=19102
2234         [ $PARALLEL == "yes" ] && skip "skip parallel run"
2235
2236         save_layout_restore_at_exit $MOUNT
2237         $LFS setstripe -c 0 -i -1 -S 0 $MOUNT
2238         wait_update $HOSTNAME "$LFS getstripe -c $MOUNT | sed 's/  *//g'" "1" 20 ||
2239                 error "stripe count $($LFS getstripe -c $MOUNT) != 1"
2240         local default_size=$($LFS getstripe -S $MOUNT)
2241         local default_offset=$($LFS getstripe -i $MOUNT)
2242         local dsize=$(do_facet $SINGLEMDS \
2243                 "$LCTL get_param -n lod.$(facet_svc $SINGLEMDS)*.stripesize")
2244         [ $default_size -eq $dsize ] ||
2245                 error "stripe size $default_size != $dsize"
2246         [ $default_offset -eq -1 ] ||
2247                 error "stripe offset $default_offset != -1"
2248 }
2249 run_test 27A "check filesystem-wide default LOV EA values"
2250
2251 test_27B() { # LU-2523
2252         test_mkdir $DIR/$tdir
2253         rm -f $DIR/$tdir/f0 $DIR/$tdir/f1
2254         touch $DIR/$tdir/f0
2255         # open f1 with O_LOV_DELAY_CREATE
2256         # rename f0 onto f1
2257         # call setstripe ioctl on open file descriptor for f1
2258         # close
2259         multiop $DIR/$tdir/f1 oO_RDWR:O_CREAT:O_LOV_DELAY_CREATE:nB1c \
2260                 $DIR/$tdir/f0
2261
2262         rm -f $DIR/$tdir/f1
2263         # open f1 with O_LOV_DELAY_CREATE
2264         # unlink f1
2265         # call setstripe ioctl on open file descriptor for f1
2266         # close
2267         multiop $DIR/$tdir/f1 oO_RDWR:O_CREAT:O_LOV_DELAY_CREATE:uB1c
2268
2269         # Allow multiop to fail in imitation of NFS's busted semantics.
2270         true
2271 }
2272 run_test 27B "call setstripe on open unlinked file/rename victim"
2273
2274 # 27C family tests full striping and overstriping
2275 test_27Ca() { #LU-2871
2276         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
2277
2278         declare -a ost_idx
2279         local index
2280         local found
2281         local i
2282         local j
2283
2284         test_mkdir $DIR/$tdir
2285         cd $DIR/$tdir
2286         for i in $(seq 0 $((OSTCOUNT - 1))); do
2287                 # set stripe across all OSTs starting from OST$i
2288                 $LFS setstripe -i $i -c -1 $tfile$i
2289                 # get striping information
2290                 ost_idx=($($LFS getstripe $tfile$i |
2291                          tail -n $((OSTCOUNT + 1)) | awk '{print $1}'))
2292                 echo ${ost_idx[@]}
2293
2294                 # check the layout
2295                 [ ${#ost_idx[@]} -eq $OSTCOUNT ] ||
2296                         error "${#ost_idx[@]} != $OSTCOUNT"
2297
2298                 for index in $(seq 0 $((OSTCOUNT - 1))); do
2299                         found=0
2300                         for j in $(echo ${ost_idx[@]}); do
2301                                 if [ $index -eq $j ]; then
2302                                         found=1
2303                                         break
2304                                 fi
2305                         done
2306                         [ $found = 1 ] ||
2307                                 error "Can not find $index in ${ost_idx[@]}"
2308                 done
2309         done
2310 }
2311 run_test 27Ca "check full striping across all OSTs"
2312
2313 test_27Cb() {
2314         [[ $($LCTL get_param mdc.*.import) =~ connect_flags.*overstriping ]] ||
2315                 skip "server does not support overstriping"
2316         [[ $OSTCOUNT -ge $(($LOV_MAX_STRIPE_COUNT / 2)) ]] &&
2317                 skip_env "too many osts, skipping"
2318
2319         test_mkdir -p $DIR/$tdir
2320         local setcount=$(($OSTCOUNT * 2))
2321         [ $setcount -ge 160 ] || large_xattr_enabled ||
2322                 skip_env "ea_inode feature disabled"
2323
2324         $LFS setstripe -C $setcount $DIR/$tdir/$tfile ||
2325                 error "setstripe failed"
2326
2327         local count=$($LFS getstripe -c $DIR/$tdir/$tfile)
2328         [ $count -eq $setcount ] ||
2329                 error "stripe count $count, should be $setcount"
2330
2331         $LFS getstripe $DIR/$tdir/$tfile 2>&1 | grep "overstriped" ||
2332                 error "overstriped should be set in pattern"
2333
2334         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=4 conv=notrunc ||
2335                 error "dd failed"
2336 }
2337 run_test 27Cb "more stripes than OSTs with -C"
2338
2339 test_27Cc() {
2340         [[ $($LCTL get_param mdc.*.import) =~ connect_flags.*overstriping ]] ||
2341                 skip "server does not support overstriping"
2342         [[ $OSTCOUNT -lt 2 ]] && skip_env "need > 1 OST"
2343
2344         test_mkdir -p $DIR/$tdir
2345         local setcount=$(($OSTCOUNT - 1))
2346
2347         [ $setcount -ge 160 ] || large_xattr_enabled ||
2348                 skip_env "ea_inode feature disabled"
2349
2350         $LFS setstripe -C $setcount $DIR/$tdir/$tfile ||
2351                 error "setstripe failed"
2352
2353         local count=$($LFS getstripe -c $DIR/$tdir/$tfile)
2354         [ $count -eq $setcount ] ||
2355                 error "stripe count $count, should be $setcount"
2356
2357         $LFS getstripe $DIR/$tdir/$tfile 2>&1 | grep "overstriped" &&
2358                 error "overstriped should not be set in pattern"
2359
2360         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=4 conv=notrunc ||
2361                 error "dd failed"
2362 }
2363 run_test 27Cc "fewer stripes than OSTs does not set overstriping"
2364
2365 test_27Cd() {
2366         [[ $($LCTL get_param mdc.*.import) =~ connect_flags.*overstriping ]] ||
2367                 skip "server does not support overstriping"
2368         [[ $OSTCOUNT -lt 2 ]] && skip_env "need > 1 OST"
2369         large_xattr_enabled || skip_env "ea_inode feature disabled"
2370
2371         test_mkdir -p $DIR/$tdir
2372         local setcount=$LOV_MAX_STRIPE_COUNT
2373
2374         $LFS setstripe -C $setcount $DIR/$tdir/$tfile ||
2375                 error "setstripe failed"
2376
2377         local count=$($LFS getstripe -c $DIR/$tdir/$tfile)
2378         [ $count -eq $setcount ] ||
2379                 error "stripe count $count, should be $setcount"
2380
2381         $LFS getstripe $DIR/$tdir/$tfile 2>&1 | grep "overstriped" ||
2382                 error "overstriped should be set in pattern"
2383
2384         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=4 conv=notrunc ||
2385                 error "dd failed"
2386
2387         rm -f $DIR/$tdir/$tfile || error "Delete $tfile failed"
2388 }
2389 run_test 27Cd "test maximum stripe count"
2390
2391 test_27Ce() {
2392         [[ $($LCTL get_param mdc.*.import) =~ connect_flags.*overstriping ]] ||
2393                 skip "server does not support overstriping"
2394         test_mkdir -p $DIR/$tdir
2395
2396         pool_add $TESTNAME || error "Pool creation failed"
2397         pool_add_targets $TESTNAME 0 || error "pool_add_targets failed"
2398
2399         local setcount=8
2400
2401         $LFS setstripe  -C $setcount -p "$TESTNAME" $DIR/$tdir/$tfile ||
2402                 error "setstripe failed"
2403
2404         local count=$($LFS getstripe -c $DIR/$tdir/$tfile)
2405         [ $count -eq $setcount ] ||
2406                 error "stripe count $count, should be $setcount"
2407
2408         $LFS getstripe $DIR/$tdir/$tfile 2>&1 | grep "overstriped" ||
2409                 error "overstriped should be set in pattern"
2410
2411         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=4 conv=notrunc ||
2412                 error "dd failed"
2413
2414         rm -f $DIR/$tdir/$tfile || error "Delete $tfile failed"
2415 }
2416 run_test 27Ce "test pool with overstriping"
2417
2418 test_27Cf() {
2419         [[ $($LCTL get_param mdc.*.import) =~ connect_flags.*overstriping ]] ||
2420                 skip "server does not support overstriping"
2421         [[ $OSTCOUNT -ge $(($LOV_MAX_STRIPE_COUNT / 2)) ]] &&
2422                 skip_env "too many osts, skipping"
2423
2424         test_mkdir -p $DIR/$tdir
2425
2426         local setcount=$(($OSTCOUNT * 2))
2427         [ $setcount -ge 160 ] || large_xattr_enabled ||
2428                 skip_env "ea_inode feature disabled"
2429
2430         $LFS setstripe  -C $setcount $DIR/$tdir/ ||
2431                 error "setstripe failed"
2432
2433         echo 1 > $DIR/$tdir/$tfile
2434
2435         local count=$($LFS getstripe -c $DIR/$tdir/$tfile)
2436         [ $count -eq $setcount ] ||
2437                 error "stripe count $count, should be $setcount"
2438
2439         $LFS getstripe $DIR/$tdir/$tfile 2>&1 | grep "overstriped" ||
2440                 error "overstriped should be set in pattern"
2441
2442         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=4 conv=notrunc ||
2443                 error "dd failed"
2444
2445         rm -f $DIR/$tdir/$tfile || error "Delete $tfile failed"
2446 }
2447 run_test 27Cf "test default inheritance with overstriping"
2448
2449 test_27D() {
2450         [ $OSTCOUNT -lt 2 ] && skip_env "needs >= 2 OSTs"
2451         [ -n "$FILESET" ] && skip "SKIP due to FILESET set"
2452         remote_mds_nodsh && skip "remote MDS with nodsh"
2453
2454         local POOL=${POOL:-testpool}
2455         local first_ost=0
2456         local last_ost=$(($OSTCOUNT - 1))
2457         local ost_step=1
2458         local ost_list=$(seq $first_ost $ost_step $last_ost)
2459         local ost_range="$first_ost $last_ost $ost_step"
2460
2461         test_mkdir $DIR/$tdir
2462         pool_add $POOL || error "pool_add failed"
2463         pool_add_targets $POOL $ost_range || error "pool_add_targets failed"
2464
2465         local skip27D
2466         [ $MDS1_VERSION -lt $(version_code 2.8.55) ] &&
2467                 skip27D+="-s 29"
2468         [ $MDS1_VERSION -lt $(version_code 2.9.55) ] ||
2469                 [ $CLIENT_VERSION -lt $(version_code 2.9.55) ] &&
2470                         skip27D+=" -s 30,31"
2471         [[ ! $($LCTL get_param mdc.*.import) =~ connect_flags.*overstriping ||
2472           $OSTCOUNT -ge $(($LOV_MAX_STRIPE_COUNT / 2)) ]] &&
2473                 skip27D+=" -s 32,33"
2474         [[ $MDS_VERSION -lt $(version_code $SEL_VER) ]] &&
2475                 skip27D+=" -s 34"
2476         llapi_layout_test -d$DIR/$tdir -p$POOL -o$OSTCOUNT $skip27D ||
2477                 error "llapi_layout_test failed"
2478
2479         destroy_test_pools || error "destroy test pools failed"
2480 }
2481 run_test 27D "validate llapi_layout API"
2482
2483 # Verify that default_easize is increased from its initial value after
2484 # accessing a widely striped file.
2485 test_27E() {
2486         [ $OSTCOUNT -lt 2 ] && skip_env "needs >= 2 OSTs"
2487         [ $CLIENT_VERSION -lt $(version_code 2.5.57) ] &&
2488                 skip "client does not have LU-3338 fix"
2489
2490         # 72 bytes is the minimum space required to store striping
2491         # information for a file striped across one OST:
2492         # (sizeof(struct lov_user_md_v3) +
2493         #  sizeof(struct lov_user_ost_data_v1))
2494         local min_easize=72
2495         $LCTL set_param -n llite.*.default_easize $min_easize ||
2496                 error "lctl set_param failed"
2497         local easize=$($LCTL get_param -n llite.*.default_easize)
2498
2499         [ $easize -eq $min_easize ] ||
2500                 error "failed to set default_easize"
2501
2502         $LFS setstripe -c $OSTCOUNT $DIR/$tfile ||
2503                 error "setstripe failed"
2504         # In order to ensure stat() call actually talks to MDS we need to
2505         # do something drastic to this file to shake off all lock, e.g.
2506         # rename it (kills lookup lock forcing cache cleaning)
2507         mv $DIR/$tfile $DIR/${tfile}-1
2508         ls -l $DIR/${tfile}-1
2509         rm $DIR/${tfile}-1
2510
2511         easize=$($LCTL get_param -n llite.*.default_easize)
2512
2513         [ $easize -gt $min_easize ] ||
2514                 error "default_easize not updated"
2515 }
2516 run_test 27E "check that default extended attribute size properly increases"
2517
2518 test_27F() { # LU-5346/LU-7975
2519         [ $PARALLEL == "yes" ] && skip "skip parallel run"
2520         [[ $OSTCOUNT -lt 2 ]] && skip "needs >= 2 OSTs"
2521         [[ $MDS1_VERSION -lt $(version_code 2.8.51) ]] &&
2522                 skip "Need MDS version at least 2.8.51"
2523         remote_ost_nodsh && skip "remote OST with nodsh"
2524
2525         test_mkdir $DIR/$tdir
2526         rm -f $DIR/$tdir/f0
2527         $LFS setstripe -c 2 $DIR/$tdir
2528
2529         # stop all OSTs to reproduce situation for LU-7975 ticket
2530         for num in $(seq $OSTCOUNT); do
2531                 stop ost$num
2532         done
2533
2534         # open/create f0 with O_LOV_DELAY_CREATE
2535         # truncate f0 to a non-0 size
2536         # close
2537         multiop $DIR/$tdir/f0 oO_RDWR:O_CREAT:O_LOV_DELAY_CREATE:T1050000c
2538
2539         $CHECKSTAT -s 1050000 $DIR/$tdir/f0 || error "checkstat failed"
2540         # open/write it again to force delayed layout creation
2541         cat /etc/hosts > $DIR/$tdir/f0 &
2542         catpid=$!
2543
2544         # restart OSTs
2545         for num in $(seq $OSTCOUNT); do
2546                 start ost$num $(ostdevname $num) $OST_MOUNT_OPTS ||
2547                         error "ost$num failed to start"
2548         done
2549
2550         wait $catpid || error "cat failed"
2551
2552         cmp /etc/hosts $DIR/$tdir/f0 || error "cmp failed"
2553         [[ $($LFS getstripe -c $DIR/$tdir/f0) == 2 ]] ||
2554                 error "wrong stripecount"
2555
2556 }
2557 run_test 27F "Client resend delayed layout creation with non-zero size"
2558
2559 test_27G() { #LU-10629
2560         [ $MDS1_VERSION -lt $(version_code 2.11.51) ] &&
2561                 skip "Need MDS version at least 2.11.51"
2562         [ -n "$FILESET" ] && skip "SKIP due to FILESET set"
2563         remote_mds_nodsh && skip "remote MDS with nodsh"
2564         local POOL=${POOL:-testpool}
2565         local ostrange="0 0 1"
2566
2567         test_mkdir $DIR/$tdir
2568         pool_add $POOL || error "pool_add failed"
2569         pool_add_targets $POOL $ostrange || error "pool_add_targets failed"
2570         $LFS setstripe -p $POOL $DIR/$tdir
2571
2572         local pool=$($LFS getstripe -p $DIR/$tdir)
2573
2574         [ "$pool" = "$POOL" ] || error "Striping failed got '$pool' not '$POOL'"
2575
2576         $LFS setstripe -d $DIR/$tdir
2577
2578         pool=$($LFS getstripe -p $DIR/$tdir)
2579
2580         rmdir $DIR/$tdir
2581
2582         [ -z "$pool" ] || error "'$pool' is not empty"
2583 }
2584 run_test 27G "Clear OST pool from stripe"
2585
2586 test_27H() {
2587         [[ $MDS1_VERSION -le $(version_code 2.11.54) ]] &&
2588                 skip "Need MDS version newer than 2.11.54"
2589         [[ $OSTCOUNT -lt 3 ]] && skip_env "needs >= 3 OSTs"
2590         test_mkdir $DIR/$tdir
2591         $LFS setstripe -o 0 -o 2 $DIR/$tdir || error "setstripe failed"
2592         touch $DIR/$tdir/$tfile
2593         $LFS getstripe -c $DIR/$tdir/$tfile
2594         [ $($LFS getstripe -c $DIR/$tdir/$tfile) -eq 2 ] ||
2595                 error "two-stripe file doesn't have two stripes"
2596
2597         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=4k count=4 || error "dd failed"
2598         $LFS getstripe -y $DIR/$tdir/$tfile
2599         (( $($LFS getstripe -y $DIR/$tdir/$tfile |
2600              egrep -c "l_ost_idx: [02]$") == "2" )) ||
2601                 error "expected l_ost_idx: [02]$ not matched"
2602
2603         # make sure ost list has been cleared
2604         local stripesize=$($LFS getstripe -S $DIR/$tdir)
2605         $LFS setstripe -S $((stripesize * 4)) -i 1 \
2606                 -c $((OSTCOUNT - 1)) $DIR/$tdir || error "setstripe"
2607         touch $DIR/$tdir/f3
2608         $LVERIFY $DIR/$tdir $DIR/$tdir/f3 || error "lverify failed"
2609 }
2610 run_test 27H "Set specific OSTs stripe"
2611
2612 test_27I() {
2613         [ $PARALLEL == "yes" ] && skip "skip parallel run"
2614         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
2615         [[ $MDS1_VERSION -gt $(version_code 2.12.52) ]] ||
2616                 skip "Need MDS version newer than 2.12.52"
2617         local pool=$TESTNAME
2618         local ostrange="1 1 1"
2619
2620         save_layout_restore_at_exit $MOUNT
2621         $LFS setstripe -c 2 -i 0 $MOUNT
2622         pool_add $pool || error "pool_add failed"
2623         pool_add_targets $pool $ostrange || "pool_add_targets failed"
2624         test_mkdir $DIR/$tdir
2625         $LFS setstripe -p $pool $DIR/$tdir
2626         $MULTIOP $DIR/$tdir/$tfile Oc || error "multiop failed"
2627         $LFS getstripe $DIR/$tdir/$tfile
2628 }
2629 run_test 27I "check that root dir striping does not break parent dir one"
2630
2631 test_27J() {
2632         [[ $(lustre_version_code $SINGLEMDS) -le $(version_code 2.12.51) ]] &&
2633                 skip "Need MDS version newer than 2.12.51"
2634
2635         test_mkdir $DIR/$tdir
2636         local uuid1=$(cat /proc/sys/kernel/random/uuid)
2637         local uuid2=$(cat /proc/sys/kernel/random/uuid)
2638
2639         # create foreign file (raw way)
2640         create_foreign_file -f $DIR/$tdir/$tfile -x "${uuid1}@${uuid2}" \
2641                 -t 1 -F 0xda08 || error "create_foreign_file failed"
2642
2643         # verify foreign file (raw way)
2644         parse_foreign_file -f $DIR/$tdir/$tfile |
2645                 grep "lov_foreign_magic: 0x0BD70BD0" ||
2646                 error "$DIR/$tdir/$tfile: invalid LOV EA foreign magic"
2647         parse_foreign_file -f $DIR/$tdir/$tfile | grep "lov_xattr_size: 89" ||
2648                 error "$DIR/$tdir/$tfile: invalid LOV EA foreign size"
2649         parse_foreign_file -f $DIR/$tdir/$tfile |
2650                 grep "lov_foreign_size: 73" ||
2651                 error "$DIR/$tdir/$tfile: invalid LOV EA foreign size"
2652         parse_foreign_file -f $DIR/$tdir/$tfile |
2653                 grep "lov_foreign_type: 1" ||
2654                 error "$DIR/$tdir/$tfile: invalid LOV EA foreign type"
2655         parse_foreign_file -f $DIR/$tdir/$tfile |
2656                 grep "lov_foreign_flags: 0x0000DA08" ||
2657                 error "$DIR/$tdir/$tfile: invalid LOV EA foreign flags"
2658         local lov=$(parse_foreign_file -f $DIR/$tdir/$tfile |
2659                 grep "lov_foreign_value: 0x" |
2660                 sed -e 's/lov_foreign_value: 0x//')
2661         local lov2=$(echo -n "${uuid1}@${uuid2}" | od -A n -t x1 -w160)
2662         [[ $lov = ${lov2// /} ]] ||
2663                 error "$DIR/$tdir/$tfile: invalid LOV EA foreign value"
2664
2665         # create foreign file (lfs + API)
2666         $LFS setstripe --foreign=daos --flags 0xda08 \
2667                 -x "${uuid1}@${uuid2}" $DIR/$tdir/${tfile}2 ||
2668                 error "$DIR/$tdir/${tfile}2: create failed"
2669
2670         $LFS getstripe -v $DIR/$tdir/${tfile}2 |
2671                 grep "lfm_magic:.*0x0BD70BD0" ||
2672                 error "$DIR/$tdir/${tfile}2: invalid LOV EA foreign magic"
2673         # lfm_length is LOV EA size - sizeof(lfm_magic) - sizeof(lfm_length)
2674         $LFS getstripe -v $DIR/$tdir/${tfile}2 | grep "lfm_length:.*73" ||
2675                 error "$DIR/$tdir/${tfile}2: invalid LOV EA foreign size"
2676         $LFS getstripe -v $DIR/$tdir/${tfile}2 | grep "lfm_type:.*daos" ||
2677                 error "$DIR/$tdir/${tfile}2: invalid LOV EA foreign type"
2678         $LFS getstripe -v $DIR/$tdir/${tfile}2 |
2679                 grep "lfm_flags:.*0x0000DA08" ||
2680                 error "$DIR/$tdir/${tfile}2: invalid LOV EA foreign flags"
2681         $LFS getstripe $DIR/$tdir/${tfile}2 |
2682                 grep "lfm_value:.*${uuid1}@${uuid2}" ||
2683                 error "$DIR/$tdir/${tfile}2: invalid LOV EA foreign value"
2684
2685         # modify striping should fail
2686         $LFS setstripe -c 2 $DIR/$tdir/$tfile &&
2687                 error "$DIR/$tdir/$tfile: setstripe should fail"
2688         $LFS setstripe -c 2 $DIR/$tdir/${tfile}2 &&
2689                 error "$DIR/$tdir/${tfile}2: setstripe should fail"
2690
2691         # R/W should fail
2692         cat $DIR/$tdir/$tfile && error "$DIR/$tdir/$tfile: read should fail"
2693         cat $DIR/$tdir/${tfile}2 &&
2694                 error "$DIR/$tdir/${tfile}2: read should fail"
2695         cat /etc/passwd > $DIR/$tdir/$tfile &&
2696                 error "$DIR/$tdir/$tfile: write should fail"
2697         cat /etc/passwd > $DIR/$tdir/${tfile}2 &&
2698                 error "$DIR/$tdir/${tfile}2: write should fail"
2699
2700         # chmod should work
2701         chmod 222 $DIR/$tdir/$tfile ||
2702                 error "$DIR/$tdir/$tfile: chmod failed"
2703         chmod 222 $DIR/$tdir/${tfile}2 ||
2704                 error "$DIR/$tdir/${tfile}2: chmod failed"
2705
2706         # chown should work
2707         chown $RUNAS_ID:$RUNAS_GID $DIR/$tdir/$tfile ||
2708                 error "$DIR/$tdir/$tfile: chown failed"
2709         chown $RUNAS_ID:$RUNAS_GID $DIR/$tdir/${tfile}2 ||
2710                 error "$DIR/$tdir/${tfile}2: chown failed"
2711
2712         # rename should work
2713         mv $DIR/$tdir/$tfile $DIR/$tdir/${tfile}.new ||
2714                 error "$DIR/$tdir/$tfile: rename of foreign file has failed"
2715         mv $DIR/$tdir/${tfile}2 $DIR/$tdir/${tfile}2.new ||
2716                 error "$DIR/$tdir/${tfile}2: rename of foreign file has failed"
2717
2718         #remove foreign file
2719         rm $DIR/$tdir/${tfile}.new ||
2720                 error "$DIR/$tdir/${tfile}.new: remove of foreign file has failed"
2721         rm $DIR/$tdir/${tfile}2.new ||
2722                 error "$DIR/$tdir/${tfile}2.new: remove of foreign file has failed"
2723 }
2724 run_test 27J "basic ops on file with foreign LOV"
2725
2726 test_27K() {
2727         [[ $(lustre_version_code $SINGLEMDS) -le $(version_code 2.12.49) ]] &&
2728                 skip "Need MDS version newer than 2.12.49"
2729
2730         test_mkdir $DIR/$tdir
2731         local uuid1=$(cat /proc/sys/kernel/random/uuid)
2732         local uuid2=$(cat /proc/sys/kernel/random/uuid)
2733
2734         # create foreign dir (raw way)
2735         create_foreign_dir -d $DIR/$tdir/$tdir -x "${uuid1}@${uuid2}" -t 1 ||
2736                 error "create_foreign_dir FAILED"
2737
2738         # verify foreign dir (raw way)
2739         parse_foreign_dir -d $DIR/$tdir/$tdir |
2740                 grep "lmv_foreign_magic:.*0xcd50cd0" ||
2741                 error "$DIR/$tdir/$tfile: invalid LMV EA magic"
2742         parse_foreign_dir -d $DIR/$tdir/$tdir | grep "lmv_xattr_size:.*89$" ||
2743                 error "$DIR/$tdir/$tdir: invalid LMV EA size"
2744         parse_foreign_dir -d $DIR/$tdir/$tdir | grep "lmv_foreign_type: 1$" ||
2745                 error "$DIR/$tdir/$tdir: invalid LMV EA type"
2746         parse_foreign_dir -d $DIR/$tdir/$tdir | grep "lmv_foreign_flags: 0$" ||
2747                 error "$DIR/$tdir/$tdir: invalid LMV EA flags"
2748         local lmv=$(parse_foreign_dir -d $DIR/$tdir/$tdir |
2749                 grep "lmv_foreign_value: 0x" |
2750                 sed 's/lmv_foreign_value: 0x//')
2751         local lmv2=$(echo -n "${uuid1}@${uuid2}" | od -A n -t x1 -w160 |
2752                 sed 's/ //g')
2753         [[ $lmv == $lmv2 ]] || error "$DIR/$tdir/$tdir: invalid LMV EA value"
2754
2755         # create foreign dir (lfs + API)
2756         $LFS mkdir --foreign=daos --xattr="${uuid1}@${uuid2}" --flags=0xda05 \
2757                 $DIR/$tdir/${tdir}2 ||
2758                 error "$DIR/$tdir/${tdir}2: create failed"
2759
2760         $LFS getdirstripe -v $DIR/$tdir/${tdir}2 |
2761                 grep "lfm_magic:.*0x0CD50CD0" ||
2762                 error "$DIR/$tdir/${tdir}2: invalid LMV EA magic"
2763         # lfm_length is LMV EA size - sizeof(lfm_magic) - sizeof(lfm_length)
2764         # - sizeof(lfm_type) - sizeof(lfm_flags)
2765         $LFS getdirstripe -v $DIR/$tdir/${tdir}2 | grep "lfm_length:.*73" ||
2766                 error "$DIR/$tdir/${tdir}2: invalid LMV EA size"
2767         $LFS getdirstripe -v $DIR/$tdir/${tdir}2 | grep "lfm_type:.*daos" ||
2768                 error "$DIR/$tdir/${tdir}2: invalid LMV EA type"
2769         $LFS getdirstripe -v $DIR/$tdir/${tdir}2 |
2770                 grep "lfm_flags:.*0x0000DA05" ||
2771                 error "$DIR/$tdir/${tdir}2: invalid LMV EA flags"
2772         $LFS getdirstripe $DIR/$tdir/${tdir}2 |
2773                 grep "lfm_value.*${uuid1}@${uuid2}" ||
2774                 error "$DIR/$tdir/${tdir}2: invalid LMV EA value"
2775
2776         # file create in dir should fail
2777         touch $DIR/$tdir/$tdir/$tfile && "$DIR/$tdir: file create should fail"
2778         touch $DIR/$tdir/${tdir}2/$tfile &&
2779                 "$DIR/${tdir}2: file create should fail"
2780
2781         # chmod should work
2782         chmod 777 $DIR/$tdir/$tdir ||
2783                 error "$DIR/$tdir: chmod failed"
2784         chmod 777 $DIR/$tdir/${tdir}2 ||
2785                 error "$DIR/${tdir}2: chmod failed"
2786
2787         # chown should work
2788         chown $RUNAS_ID:$RUNAS_GID $DIR/$tdir/$tdir ||
2789                 error "$DIR/$tdir: chown failed"
2790         chown $RUNAS_ID:$RUNAS_GID $DIR/$tdir/${tdir}2 ||
2791                 error "$DIR/${tdir}2: chown failed"
2792
2793         # rename should work
2794         mv $DIR/$tdir/$tdir $DIR/$tdir/${tdir}.new ||
2795                 error "$DIR/$tdir/$tdir: rename of foreign dir has failed"
2796         mv $DIR/$tdir/${tdir}2 $DIR/$tdir/${tdir}2.new ||
2797                 error "$DIR/$tdir/${tdir}2: rename of foreign dir has failed"
2798
2799         #remove foreign dir
2800         rmdir $DIR/$tdir/${tdir}.new ||
2801                 error "$DIR/$tdir/${tdir}.new: remove of foreign dir has failed"
2802         rmdir $DIR/$tdir/${tdir}2.new ||
2803                 error "$DIR/$tdir/${tdir}2.new: remove of foreign dir has failed"
2804 }
2805 run_test 27K "basic ops on dir with foreign LMV"
2806
2807 test_27L() {
2808         remote_mds_nodsh && skip "remote MDS with nodsh"
2809
2810         local POOL=${POOL:-$TESTNAME}
2811
2812         pool_add $POOL || error "pool_add failed"
2813
2814         lfs pool_list $MOUNT | grep -Fx "${FSNAME}.${POOL}" ||
2815                  error "pool_list does not contain ${FSNAME}.${POOL}:" \
2816                        "$(lfs pool_list $MOUNT | grep -F "${POOL}")"
2817 }
2818 run_test 27L "lfs pool_list gives correct pool name"
2819
2820 test_27M() {
2821         [[ $(lustre_version_code $SINGLEMDS) -lt $(version_code 2.12.57) ]] &&
2822                 skip "Need MDS version >= than 2.12.57"
2823         remote_mds_nodsh && skip "remote MDS with nodsh"
2824         [[ $OSTCOUNT -lt 2 ]] && skip_env "need > 1 OST"
2825
2826         test_mkdir $DIR/$tdir
2827
2828         # Set default striping on directory
2829         $LFS setstripe -C 4 $DIR/$tdir
2830
2831         echo 1 > $DIR/$tdir/${tfile}.1
2832         local count=$($LFS getstripe -c $DIR/$tdir/${tfile}.1)
2833         local setcount=4
2834         [ $count -eq $setcount ] ||
2835                 error "(1) stripe count $count, should be $setcount"
2836
2837         # Capture existing append_stripe_count setting for restore
2838         local orig_count=$(do_facet mds1 $LCTL get_param -n mdd.$FSNAME-MDT0000.append_stripe_count)
2839         local mdts=$(comma_list $(mdts_nodes))
2840         stack_trap "do_nodes $mdts $LCTL set_param mdd.*.append_stripe_count=$orig_count" EXIT
2841
2842         local appendcount=$orig_count
2843         echo 1 >> $DIR/$tdir/${tfile}.2_append
2844         count=$($LFS getstripe -c $DIR/$tdir/${tfile}.2_append)
2845         [ $count -eq $appendcount ] ||
2846                 error "(2)stripe count $count, should be $appendcount for append"
2847
2848         # Disable O_APPEND striping, verify it works
2849         do_nodes $mdts $LCTL set_param mdd.*.append_stripe_count=0
2850
2851         # Should now get the default striping, which is 4
2852         setcount=4
2853         echo 1 >> $DIR/$tdir/${tfile}.3_append
2854         count=$($LFS getstripe -c $DIR/$tdir/${tfile}.3_append)
2855         [ $count -eq $setcount ] ||
2856                 error "(3) stripe count $count, should be $setcount"
2857
2858         # Try changing the stripe count for append files
2859         do_nodes $mdts $LCTL set_param mdd.*.append_stripe_count=2
2860
2861         # Append striping is now 2 (directory default is still 4)
2862         appendcount=2
2863         echo 1 >> $DIR/$tdir/${tfile}.4_append
2864         count=$($LFS getstripe -c $DIR/$tdir/${tfile}.4_append)
2865         [ $count -eq $appendcount ] ||
2866                 error "(4) stripe count $count, should be $appendcount for append"
2867
2868         # Test append stripe count of -1
2869         do_nodes $mdts $LCTL set_param mdd.*.append_stripe_count=-1
2870         appendcount=$OSTCOUNT
2871         echo 1 >> $DIR/$tdir/${tfile}.5
2872         count=$($LFS getstripe -c $DIR/$tdir/${tfile}.5)
2873         [ $count -eq $appendcount ] ||
2874                 error "(5) stripe count $count, should be $appendcount for append"
2875
2876         # Set append striping back to default of 1
2877         do_nodes $mdts $LCTL set_param mdd.*.append_stripe_count=1
2878
2879         # Try a new default striping, PFL + DOM
2880         $LFS setstripe -L mdt -E 1M -E -1 -c 2 $DIR/$tdir
2881
2882         # Create normal DOM file, DOM returns stripe count == 0
2883         setcount=0
2884         touch $DIR/$tdir/${tfile}.6
2885         count=$($LFS getstripe -c $DIR/$tdir/${tfile}.6)
2886         [ $count -eq $setcount ] ||
2887                 error "(6) stripe count $count, should be $setcount"
2888
2889         # Show
2890         appendcount=1
2891         echo 1 >> $DIR/$tdir/${tfile}.7_append
2892         count=$($LFS getstripe -c $DIR/$tdir/${tfile}.7_append)
2893         [ $count -eq $appendcount ] ||
2894                 error "(7) stripe count $count, should be $appendcount for append"
2895
2896         # Clean up DOM layout
2897         $LFS setstripe -d $DIR/$tdir
2898
2899         # Now test that append striping works when layout is from root
2900         $LFS setstripe -c 2 $MOUNT
2901         # Make a special directory for this
2902         mkdir $DIR/${tdir}/${tdir}.2
2903         stack_trap "$LFS setstripe -d $MOUNT" EXIT
2904
2905         # Verify for normal file
2906         setcount=2
2907         echo 1 > $DIR/${tdir}/${tdir}.2/${tfile}.8
2908         count=$($LFS getstripe -c $DIR/$tdir/${tdir}.2/${tfile}.8)
2909         [ $count -eq $setcount ] ||
2910                 error "(8) stripe count $count, should be $setcount"
2911
2912         appendcount=1
2913         echo 1 >> $DIR/${tdir}/${tdir}.2/${tfile}.9_append
2914         count=$($LFS getstripe -c $DIR/${tdir}/${tdir}.2/${tfile}.9_append)
2915         [ $count -eq $appendcount ] ||
2916                 error "(9) stripe count $count, should be $appendcount for append"
2917
2918         # Now test O_APPEND striping with pools
2919         do_nodes $mdts $LCTL set_param mdd.*.append_pool="$TESTNAME"
2920         stack_trap "do_nodes $mdts $LCTL set_param mdd.*.append_pool='none'" EXIT
2921
2922         # Create the pool
2923         pool_add $TESTNAME || error "pool creation failed"
2924         pool_add_targets $TESTNAME 0 1 || error "Pool add targets failed"
2925
2926         echo 1 >> $DIR/$tdir/${tfile}.10_append
2927
2928         pool=$($LFS getstripe -p $DIR/$tdir/${tfile}.10_append)
2929         [ "$pool" = "$TESTNAME" ] || error "(10) incorrect pool: $pool"
2930
2931         # Check that count is still correct
2932         appendcount=1
2933         echo 1 >> $DIR/$tdir/${tfile}.11_append
2934         count=$($LFS getstripe -c $DIR/$tdir/${tfile}.11_append)
2935         [ $count -eq $appendcount ] ||
2936                 error "(11) stripe count $count, should be $appendcount for append"
2937
2938         # Disable O_APPEND stripe count, verify pool works separately
2939         do_nodes $mdts $LCTL set_param mdd.*.append_stripe_count=0
2940
2941         echo 1 >> $DIR/$tdir/${tfile}.12_append
2942
2943         pool=$($LFS getstripe -p $DIR/$tdir/${tfile}.12_append)
2944         [ "$pool" = "$TESTNAME" ] || error "(12) incorrect pool: $pool"
2945
2946         # Remove pool setting, verify it's not applied
2947         do_nodes $mdts $LCTL set_param mdd.*.append_pool='none'
2948
2949         echo 1 >> $DIR/$tdir/${tfile}.13_append
2950
2951         pool=$($LFS getstripe -p $DIR/$tdir/${tfile}.13_append)
2952         [ "$pool" = "" ] || error "(13) pool found: $pool"
2953 }
2954 run_test 27M "test O_APPEND striping"
2955
2956 test_27N() {
2957         combined_mgs_mds && skip "needs separate MGS/MDT"
2958
2959         pool_add $TESTNAME || error "pool_add failed"
2960         do_facet mgs "$LCTL pool_list $FSNAME" |
2961                 grep -Fx "${FSNAME}.${TESTNAME}" ||
2962                 error "lctl pool_list on MGS failed"
2963 }
2964 run_test 27N "lctl pool_list on separate MGS gives correct pool name"
2965
2966 # createtest also checks that device nodes are created and
2967 # then visible correctly (#2091)
2968 test_28() { # bug 2091
2969         test_mkdir $DIR/d28
2970         $CREATETEST $DIR/d28/ct || error "createtest failed"
2971 }
2972 run_test 28 "create/mknod/mkdir with bad file types ============"
2973
2974 test_29() {
2975         [ $PARALLEL == "yes" ] && skip "skip parallel run"
2976
2977         sync; sleep 1; sync # flush out any dirty pages from previous tests
2978         cancel_lru_locks
2979         test_mkdir $DIR/d29
2980         touch $DIR/d29/foo
2981         log 'first d29'
2982         ls -l $DIR/d29
2983
2984         declare -i LOCKCOUNTORIG=0
2985         for lock_count in $(lctl get_param -n ldlm.namespaces.*mdc*.lock_count); do
2986                 let LOCKCOUNTORIG=$LOCKCOUNTORIG+$lock_count
2987         done
2988         [ $LOCKCOUNTORIG -eq 0 ] && error "No mdc lock count" && return 1
2989
2990         declare -i LOCKUNUSEDCOUNTORIG=0
2991         for unused_count in $(lctl get_param -n ldlm.namespaces.*mdc*.lock_unused_count); do
2992                 let LOCKUNUSEDCOUNTORIG=$LOCKUNUSEDCOUNTORIG+$unused_count
2993         done
2994
2995         log 'second d29'
2996         ls -l $DIR/d29
2997         log 'done'
2998
2999         declare -i LOCKCOUNTCURRENT=0
3000         for lock_count in $(lctl get_param -n ldlm.namespaces.*mdc*.lock_count); do
3001                 let LOCKCOUNTCURRENT=$LOCKCOUNTCURRENT+$lock_count
3002         done
3003
3004         declare -i LOCKUNUSEDCOUNTCURRENT=0
3005         for unused_count in $(lctl get_param -n ldlm.namespaces.*mdc*.lock_unused_count); do
3006                 let LOCKUNUSEDCOUNTCURRENT=$LOCKUNUSEDCOUNTCURRENT+$unused_count
3007         done
3008
3009         if [[ $LOCKCOUNTCURRENT -gt $LOCKCOUNTORIG ]]; then
3010                 $LCTL set_param -n ldlm.dump_namespaces ""
3011                 error "CURRENT: $LOCKCOUNTCURRENT > $LOCKCOUNTORIG"
3012                 $LCTL dk | sort -k4 -t: > $TMP/test_29.dk
3013                 log "dumped log to $TMP/test_29.dk (bug 5793)"
3014                 return 2
3015         fi
3016         if [[ $LOCKUNUSEDCOUNTCURRENT -gt $LOCKUNUSEDCOUNTORIG ]]; then
3017                 error "UNUSED: $LOCKUNUSEDCOUNTCURRENT > $LOCKUNUSEDCOUNTORIG"
3018                 $LCTL dk | sort -k4 -t: > $TMP/test_29.dk
3019                 log "dumped log to $TMP/test_29.dk (bug 5793)"
3020                 return 3
3021         fi
3022 }
3023 run_test 29 "IT_GETATTR regression  ============================"
3024
3025 test_30a() { # was test_30
3026         cp $(which ls) $DIR || cp /bin/ls $DIR
3027         $DIR/ls / || error "Can't execute binary from lustre"
3028         rm $DIR/ls
3029 }
3030 run_test 30a "execute binary from Lustre (execve) =============="
3031
3032 test_30b() {
3033         cp `which ls` $DIR || cp /bin/ls $DIR
3034         chmod go+rx $DIR/ls
3035         $RUNAS $DIR/ls / || error "Can't execute binary from lustre as non-root"
3036         rm $DIR/ls
3037 }
3038 run_test 30b "execute binary from Lustre as non-root ==========="
3039
3040 test_30c() { # b=22376
3041         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3042
3043         cp `which ls` $DIR || cp /bin/ls $DIR
3044         chmod a-rw $DIR/ls
3045         cancel_lru_locks mdc
3046         cancel_lru_locks osc
3047         $RUNAS $DIR/ls / || error "Can't execute binary from lustre"
3048         rm -f $DIR/ls
3049 }
3050 run_test 30c "execute binary from Lustre without read perms ===="
3051
3052 test_31a() {
3053         $OPENUNLINK $DIR/f31 $DIR/f31 || error "openunlink failed"
3054         $CHECKSTAT -a $DIR/f31 || error "$DIR/f31 exists"
3055 }
3056 run_test 31a "open-unlink file =================================="
3057
3058 test_31b() {
3059         touch $DIR/f31 || error "touch $DIR/f31 failed"
3060         ln $DIR/f31 $DIR/f31b || error "ln failed"
3061         $MULTIOP $DIR/f31b Ouc || error "multiop failed"
3062         $CHECKSTAT -t file $DIR/f31 || error "$DIR/f31 not file type"
3063 }
3064 run_test 31b "unlink file with multiple links while open ======="
3065
3066 test_31c() {
3067         touch $DIR/f31 || error "touch $DIR/f31 failed"
3068         ln $DIR/f31 $DIR/f31c || error "ln failed"
3069         multiop_bg_pause $DIR/f31 O_uc ||
3070                 error "multiop_bg_pause for $DIR/f31 failed"
3071         MULTIPID=$!
3072         $MULTIOP $DIR/f31c Ouc
3073         kill -USR1 $MULTIPID
3074         wait $MULTIPID
3075 }
3076 run_test 31c "open-unlink file with multiple links ============="
3077
3078 test_31d() {
3079         opendirunlink $DIR/d31d $DIR/d31d || error "opendirunlink failed"
3080         $CHECKSTAT -a $DIR/d31d || error "$DIR/d31d exists"
3081 }
3082 run_test 31d "remove of open directory ========================="
3083
3084 test_31e() { # bug 2904
3085         openfilleddirunlink $DIR/d31e || error "openfilleddirunlink failed"
3086 }
3087 run_test 31e "remove of open non-empty directory ==============="
3088
3089 test_31f() { # bug 4554
3090         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3091
3092         set -vx
3093         test_mkdir $DIR/d31f
3094         $LFS setstripe -S 1048576 -c 1 $DIR/d31f
3095         cp /etc/hosts $DIR/d31f
3096         ls -l $DIR/d31f
3097         $LFS getstripe $DIR/d31f/hosts
3098         multiop_bg_pause $DIR/d31f D_c || return 1
3099         MULTIPID=$!
3100
3101         rm -rv $DIR/d31f || error "first of $DIR/d31f"
3102         test_mkdir $DIR/d31f
3103         $LFS setstripe -S 1048576 -c 1 $DIR/d31f
3104         cp /etc/hosts $DIR/d31f
3105         ls -l $DIR/d31f
3106         $LFS getstripe $DIR/d31f/hosts
3107         multiop_bg_pause $DIR/d31f D_c || return 1
3108         MULTIPID2=$!
3109
3110         kill -USR1 $MULTIPID || error "first opendir $MULTIPID not running"
3111         wait $MULTIPID || error "first opendir $MULTIPID failed"
3112
3113         sleep 6
3114
3115         kill -USR1 $MULTIPID2 || error "second opendir $MULTIPID not running"
3116         wait $MULTIPID2 || error "second opendir $MULTIPID2 failed"
3117         set +vx
3118 }
3119 run_test 31f "remove of open directory with open-unlink file ==="
3120
3121 test_31g() {
3122         echo "-- cross directory link --"
3123         test_mkdir -c1 $DIR/${tdir}ga
3124         test_mkdir -c1 $DIR/${tdir}gb
3125         touch $DIR/${tdir}ga/f
3126         ln $DIR/${tdir}ga/f $DIR/${tdir}gb/g
3127         $CHECKSTAT -t file $DIR/${tdir}ga/f || error "source"
3128         [ `stat -c%h $DIR/${tdir}ga/f` == '2' ] || error "source nlink"
3129         $CHECKSTAT -t file $DIR/${tdir}gb/g || error "target"
3130         [ `stat -c%h $DIR/${tdir}gb/g` == '2' ] || error "target nlink"
3131 }
3132 run_test 31g "cross directory link==============="
3133
3134 test_31h() {
3135         echo "-- cross directory link --"
3136         test_mkdir -c1 $DIR/${tdir}
3137         test_mkdir -c1 $DIR/${tdir}/dir
3138         touch $DIR/${tdir}/f
3139         ln $DIR/${tdir}/f $DIR/${tdir}/dir/g
3140         $CHECKSTAT -t file $DIR/${tdir}/f || error "source"
3141         [ `stat -c%h $DIR/${tdir}/f` == '2' ] || error "source nlink"
3142         $CHECKSTAT -t file $DIR/${tdir}/dir/g || error "target"
3143         [ `stat -c%h $DIR/${tdir}/dir/g` == '2' ] || error "target nlink"
3144 }
3145 run_test 31h "cross directory link under child==============="
3146
3147 test_31i() {
3148         echo "-- cross directory link --"
3149         test_mkdir -c1 $DIR/$tdir
3150         test_mkdir -c1 $DIR/$tdir/dir
3151         touch $DIR/$tdir/dir/f
3152         ln $DIR/$tdir/dir/f $DIR/$tdir/g
3153         $CHECKSTAT -t file $DIR/$tdir/dir/f || error "source"
3154         [ `stat -c%h $DIR/$tdir/dir/f` == '2' ] || error "source nlink"
3155         $CHECKSTAT -t file $DIR/$tdir/g || error "target"
3156         [ `stat -c%h $DIR/$tdir/g` == '2' ] || error "target nlink"
3157 }
3158 run_test 31i "cross directory link under parent==============="
3159
3160 test_31j() {
3161         test_mkdir -c1 -p $DIR/$tdir
3162         test_mkdir -c1 -p $DIR/$tdir/dir1
3163         ln $DIR/$tdir/dir1 $DIR/$tdir/dir2 && error "ln for dir"
3164         link $DIR/$tdir/dir1 $DIR/$tdir/dir3 && error "link for dir"
3165         mlink $DIR/$tdir/dir1 $DIR/$tdir/dir4 && error "mlink for dir"
3166         mlink $DIR/$tdir/dir1 $DIR/$tdir/dir1 && error "mlink to the same dir"
3167         return 0
3168 }
3169 run_test 31j "link for directory==============="
3170
3171 test_31k() {
3172         test_mkdir -c1 -p $DIR/$tdir
3173         touch $DIR/$tdir/s
3174         touch $DIR/$tdir/exist
3175         mlink $DIR/$tdir/s $DIR/$tdir/t || error "mlink"
3176         mlink $DIR/$tdir/s $DIR/$tdir/exist && error "mlink to exist file"
3177         mlink $DIR/$tdir/s $DIR/$tdir/s && error "mlink to the same file"
3178         mlink $DIR/$tdir/s $DIR/$tdir && error "mlink to parent dir"
3179         mlink $DIR/$tdir $DIR/$tdir/s && error "mlink parent dir to target"
3180         mlink $DIR/$tdir/not-exist $DIR/$tdir/foo && error "mlink non-existing to new"
3181         mlink $DIR/$tdir/not-exist $DIR/$tdir/s && error "mlink non-existing to exist"
3182         return 0
3183 }
3184 run_test 31k "link to file: the same, non-existing, dir==============="
3185
3186 test_31m() {
3187         mkdir $DIR/d31m
3188         touch $DIR/d31m/s
3189         mkdir $DIR/d31m2
3190         touch $DIR/d31m2/exist
3191         mlink $DIR/d31m/s $DIR/d31m2/t || error "mlink"
3192         mlink $DIR/d31m/s $DIR/d31m2/exist && error "mlink to exist file"
3193         mlink $DIR/d31m/s $DIR/d31m2 && error "mlink to parent dir"
3194         mlink $DIR/d31m2 $DIR/d31m/s && error "mlink parent dir to target"
3195         mlink $DIR/d31m/not-exist $DIR/d31m2/foo && error "mlink non-existing to new"
3196         mlink $DIR/d31m/not-exist $DIR/d31m2/s && error "mlink non-existing to exist"
3197         return 0
3198 }
3199 run_test 31m "link to file: the same, non-existing, dir==============="
3200
3201 test_31n() {
3202         touch $DIR/$tfile || error "cannot create '$DIR/$tfile'"
3203         nlink=$(stat --format=%h $DIR/$tfile)
3204         [ ${nlink:--1} -eq 1 ] || error "nlink is $nlink, expected 1"
3205         local fd=$(free_fd)
3206         local cmd="exec $fd<$DIR/$tfile"
3207         eval $cmd
3208         cmd="exec $fd<&-"
3209         trap "eval $cmd" EXIT
3210         nlink=$(stat --dereference --format=%h /proc/self/fd/$fd)
3211         [ ${nlink:--1} -eq 1 ] || error "nlink is $nlink, expected 1"
3212         rm $DIR/$tfile || error "cannot remove '$DIR/$tfile'"
3213         nlink=$(stat --dereference --format=%h /proc/self/fd/$fd)
3214         [ ${nlink:--1} -eq 0 ] || error "nlink is $nlink, expected 0"
3215         eval $cmd
3216 }
3217 run_test 31n "check link count of unlinked file"
3218
3219 link_one() {
3220         local tempfile=$(mktemp $1_XXXXXX)
3221         mlink $tempfile $1 2> /dev/null &&
3222                 echo "$BASHPID: link $tempfile to $1 succeeded"
3223         munlink $tempfile
3224 }
3225
3226 test_31o() { # LU-2901
3227         test_mkdir $DIR/$tdir
3228         for LOOP in $(seq 100); do
3229                 rm -f $DIR/$tdir/$tfile*
3230                 for THREAD in $(seq 8); do
3231                         link_one $DIR/$tdir/$tfile.$LOOP &
3232                 done
3233                 wait
3234                 local LINKS=$(ls -1 $DIR/$tdir | grep -c $tfile.$LOOP)
3235                 [[ $LINKS -gt 1 ]] && ls $DIR/$tdir &&
3236                         error "$LINKS duplicate links to $tfile.$LOOP" &&
3237                         break || true
3238         done
3239 }
3240 run_test 31o "duplicate hard links with same filename"
3241
3242 test_31p() {
3243         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
3244
3245         test_mkdir $DIR/$tdir
3246         $LFS setdirstripe -i0 -c2 $DIR/$tdir/striped_dir
3247         $LFS setdirstripe -D -c2 -H all_char $DIR/$tdir/striped_dir
3248
3249         opendirunlink $DIR/$tdir/striped_dir/test1 ||
3250                 error "open unlink test1 failed"
3251         opendirunlink $DIR/$tdir/striped_dir/test2 ||
3252                 error "open unlink test2 failed"
3253
3254         $CHECKSTAT -a $DIR/$tdir/striped_dir/test1 ||
3255                 error "test1 still exists"
3256         $CHECKSTAT -a $DIR/$tdir/striped_dir/test2 ||
3257                 error "test2 still exists"
3258 }
3259 run_test 31p "remove of open striped directory"
3260
3261 cleanup_test32_mount() {
3262         local rc=0
3263         trap 0
3264         local loopdev=$(losetup -a | grep $EXT2_DEV | sed -ne 's/:.*$//p')
3265         $UMOUNT $DIR/$tdir/ext2-mountpoint || rc=$?
3266         losetup -d $loopdev || true
3267         rm -rf $DIR/$tdir
3268         return $rc
3269 }
3270
3271 test_32a() {
3272         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3273
3274         echo "== more mountpoints and symlinks ================="
3275         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
3276         trap cleanup_test32_mount EXIT
3277         test_mkdir -p $DIR/$tdir/ext2-mountpoint
3278         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint ||
3279                 error "mount failed for $EXT2_DEV $DIR/$tdir/ext2-mountpoint"
3280         $CHECKSTAT -t dir $DIR/$tdir/ext2-mountpoint/.. ||
3281                 error "$DIR/$tdir/ext2-mountpoint/.. not dir type"
3282         cleanup_test32_mount
3283 }
3284 run_test 32a "stat d32a/ext2-mountpoint/.. ====================="
3285
3286 test_32b() {
3287         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3288
3289         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
3290         trap cleanup_test32_mount EXIT
3291         test_mkdir -p $DIR/$tdir/ext2-mountpoint
3292         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint ||
3293                 error "mount failed for $EXT2_DEV $DIR/$tdir/ext2-mountpoint"
3294         ls -al $DIR/$tdir/ext2-mountpoint/.. ||
3295                 error "Can't list $DIR/$tdir/ext2-mountpoint/.."
3296         cleanup_test32_mount
3297 }
3298 run_test 32b "open d32b/ext2-mountpoint/.. ====================="
3299
3300 test_32c() {
3301         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3302
3303         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
3304         trap cleanup_test32_mount EXIT
3305         test_mkdir -p $DIR/$tdir/ext2-mountpoint
3306         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint ||
3307                 error "mount failed for $EXT2_DEV $DIR/$tdir/ext2-mountpoint"
3308         test_mkdir -p $DIR/$tdir/d2/test_dir
3309         $CHECKSTAT -t dir $DIR/$tdir/ext2-mountpoint/../d2/test_dir ||
3310                 error "$DIR/$tdir/ext2-mountpoint/../d2/test_dir not dir type"
3311         cleanup_test32_mount
3312 }
3313 run_test 32c "stat d32c/ext2-mountpoint/../d2/test_dir ========="
3314
3315 test_32d() {
3316         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3317
3318         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
3319         trap cleanup_test32_mount EXIT
3320         test_mkdir -p $DIR/$tdir/ext2-mountpoint
3321         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint ||
3322                 error "mount failed for $EXT2_DEV $DIR/$tdir/ext2-mountpoint"
3323         test_mkdir -p $DIR/$tdir/d2/test_dir
3324         ls -al $DIR/$tdir/ext2-mountpoint/../d2/test_dir ||
3325                 error "Can't list $DIR/$tdir/ext2-mountpoint/../d2/test_dir"
3326         cleanup_test32_mount
3327 }
3328 run_test 32d "open d32d/ext2-mountpoint/../d2/test_dir"
3329
3330 test_32e() {
3331         rm -fr $DIR/$tdir
3332         test_mkdir -p $DIR/$tdir/tmp
3333         local tmp_dir=$DIR/$tdir/tmp
3334         ln -s $DIR/$tdir $tmp_dir/symlink11
3335         ln -s $tmp_dir/symlink11 $tmp_dir/../symlink01
3336         $CHECKSTAT -t link $DIR/$tdir/tmp/symlink11 || error "symlink11 bad"
3337         $CHECKSTAT -t link $DIR/$tdir/symlink01 || error "symlink01 bad"
3338 }
3339 run_test 32e "stat d32e/symlink->tmp/symlink->lustre-subdir"
3340
3341 test_32f() {
3342         rm -fr $DIR/$tdir
3343         test_mkdir -p $DIR/$tdir/tmp
3344         local tmp_dir=$DIR/$tdir/tmp
3345         ln -s $DIR/$tdir $tmp_dir/symlink11
3346         ln -s $tmp_dir/symlink11 $tmp_dir/../symlink01
3347         ls $DIR/$tdir/tmp/symlink11  || error "symlink11 bad"
3348         ls $DIR/$tdir/symlink01 || error "symlink01 bad"
3349 }
3350 run_test 32f "open d32f/symlink->tmp/symlink->lustre-subdir"
3351
3352 test_32g() {
3353         local tmp_dir=$DIR/$tdir/tmp
3354         test_mkdir -p $tmp_dir
3355         test_mkdir $DIR/${tdir}2
3356         ln -s $DIR/${tdir}2 $tmp_dir/symlink12
3357         ln -s $tmp_dir/symlink12 $tmp_dir/../symlink02
3358         $CHECKSTAT -t link $tmp_dir/symlink12 || error "symlink12 not a link"
3359         $CHECKSTAT -t link $DIR/$tdir/symlink02 || error "symlink02 not a link"
3360         $CHECKSTAT -t dir -f $tmp_dir/symlink12 || error "symlink12 not a dir"
3361         $CHECKSTAT -t dir -f $DIR/$tdir/symlink02 || error "symlink12 not a dir"
3362 }
3363 run_test 32g "stat d32g/symlink->tmp/symlink->lustre-subdir/${tdir}2"
3364
3365 test_32h() {
3366         rm -fr $DIR/$tdir $DIR/${tdir}2
3367         tmp_dir=$DIR/$tdir/tmp
3368         test_mkdir -p $tmp_dir
3369         test_mkdir $DIR/${tdir}2
3370         ln -s $DIR/${tdir}2 $tmp_dir/symlink12
3371         ln -s $tmp_dir/symlink12 $tmp_dir/../symlink02
3372         ls $tmp_dir/symlink12 || error "listing symlink12"
3373         ls $DIR/$tdir/symlink02  || error "listing symlink02"
3374 }
3375 run_test 32h "open d32h/symlink->tmp/symlink->lustre-subdir/${tdir}2"
3376
3377 test_32i() {
3378         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3379
3380         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
3381         trap cleanup_test32_mount EXIT
3382         test_mkdir -p $DIR/$tdir/ext2-mountpoint
3383         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint ||
3384                 error "mount failed for $EXT2_DEV $DIR/$tdir/ext2-mountpoint"
3385         touch $DIR/$tdir/test_file
3386         $CHECKSTAT -t file $DIR/$tdir/ext2-mountpoint/../test_file ||
3387                 error "$DIR/$tdir/ext2-mountpoint/../test_file not file type"
3388         cleanup_test32_mount
3389 }
3390 run_test 32i "stat d32i/ext2-mountpoint/../test_file ==========="
3391
3392 test_32j() {
3393         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3394
3395         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
3396         trap cleanup_test32_mount EXIT
3397         test_mkdir -p $DIR/$tdir/ext2-mountpoint
3398         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint ||
3399                 error "mount failed for $EXT2_DEV $DIR/$tdir/ext2-mountpoint"
3400         touch $DIR/$tdir/test_file
3401         cat $DIR/$tdir/ext2-mountpoint/../test_file ||
3402                 error "Can't open $DIR/$tdir/ext2-mountpoint/../test_file"
3403         cleanup_test32_mount
3404 }
3405 run_test 32j "open d32j/ext2-mountpoint/../test_file ==========="
3406
3407 test_32k() {
3408         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3409
3410         rm -fr $DIR/$tdir
3411         trap cleanup_test32_mount EXIT
3412         test_mkdir -p $DIR/$tdir/ext2-mountpoint
3413         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint ||
3414                 error "mount failed for $EXT2_DEV $DIR/$tdir/ext2-mountpoint"
3415         test_mkdir -p $DIR/$tdir/d2
3416         touch $DIR/$tdir/d2/test_file || error "touch failed"
3417         $CHECKSTAT -t file $DIR/$tdir/ext2-mountpoint/../d2/test_file ||
3418                 error "$DIR/$tdir/ext2-mountpoint/../d2/test_file not file type"
3419         cleanup_test32_mount
3420 }
3421 run_test 32k "stat d32k/ext2-mountpoint/../d2/test_file ========"
3422
3423 test_32l() {
3424         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3425
3426         rm -fr $DIR/$tdir
3427         trap cleanup_test32_mount EXIT
3428         test_mkdir -p $DIR/$tdir/ext2-mountpoint
3429         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint ||
3430                 error "mount failed for $EXT2_DEV $DIR/$tdir/ext2-mountpoint"
3431         test_mkdir -p $DIR/$tdir/d2
3432         touch $DIR/$tdir/d2/test_file || error "touch failed"
3433         cat  $DIR/$tdir/ext2-mountpoint/../d2/test_file ||
3434                 error "Can't open $DIR/$tdir/ext2-mountpoint/../d2/test_file"
3435         cleanup_test32_mount
3436 }
3437 run_test 32l "open d32l/ext2-mountpoint/../d2/test_file ========"
3438
3439 test_32m() {
3440         rm -fr $DIR/d32m
3441         test_mkdir -p $DIR/d32m/tmp
3442         TMP_DIR=$DIR/d32m/tmp
3443         ln -s $DIR $TMP_DIR/symlink11
3444         ln -s $TMP_DIR/symlink11 $TMP_DIR/../symlink01
3445         $CHECKSTAT -t link $DIR/d32m/tmp/symlink11 ||
3446                 error "symlink11 not a link"
3447         $CHECKSTAT -t link $DIR/d32m/symlink01 ||
3448                 error "symlink01 not a link"
3449 }
3450 run_test 32m "stat d32m/symlink->tmp/symlink->lustre-root ======"
3451
3452 test_32n() {
3453         rm -fr $DIR/d32n
3454         test_mkdir -p $DIR/d32n/tmp
3455         TMP_DIR=$DIR/d32n/tmp
3456         ln -s $DIR $TMP_DIR/symlink11
3457         ln -s $TMP_DIR/symlink11 $TMP_DIR/../symlink01
3458         ls -l $DIR/d32n/tmp/symlink11  || error "listing symlink11"
3459         ls -l $DIR/d32n/symlink01 || error "listing symlink01"
3460 }
3461 run_test 32n "open d32n/symlink->tmp/symlink->lustre-root ======"
3462
3463 test_32o() {
3464         touch $DIR/$tfile
3465         test_mkdir -p $DIR/d32o/tmp
3466         TMP_DIR=$DIR/d32o/tmp
3467         ln -s $DIR/$tfile $TMP_DIR/symlink12
3468         ln -s $TMP_DIR/symlink12 $TMP_DIR/../symlink02
3469         $CHECKSTAT -t link $DIR/d32o/tmp/symlink12 ||
3470                 error "symlink12 not a link"
3471         $CHECKSTAT -t link $DIR/d32o/symlink02 || error "symlink02 not a link"
3472         $CHECKSTAT -t file -f $DIR/d32o/tmp/symlink12 ||
3473                 error "$DIR/d32o/tmp/symlink12 not file type"
3474         $CHECKSTAT -t file -f $DIR/d32o/symlink02 ||
3475                 error "$DIR/d32o/symlink02 not file type"
3476 }
3477 run_test 32o "stat d32o/symlink->tmp/symlink->lustre-root/$tfile"
3478
3479 test_32p() {
3480         log 32p_1
3481         rm -fr $DIR/d32p
3482         log 32p_2
3483         rm -f $DIR/$tfile
3484         log 32p_3
3485         touch $DIR/$tfile
3486         log 32p_4
3487         test_mkdir -p $DIR/d32p/tmp
3488         log 32p_5
3489         TMP_DIR=$DIR/d32p/tmp
3490         log 32p_6
3491         ln -s $DIR/$tfile $TMP_DIR/symlink12
3492         log 32p_7
3493         ln -s $TMP_DIR/symlink12 $TMP_DIR/../symlink02
3494         log 32p_8
3495         cat $DIR/d32p/tmp/symlink12 ||
3496                 error "Can't open $DIR/d32p/tmp/symlink12"
3497         log 32p_9
3498         cat $DIR/d32p/symlink02 || error "Can't open $DIR/d32p/symlink02"
3499         log 32p_10
3500 }
3501 run_test 32p "open d32p/symlink->tmp/symlink->lustre-root/$tfile"
3502
3503 test_32q() {
3504         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3505
3506         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
3507         trap cleanup_test32_mount EXIT
3508         test_mkdir -p $DIR/$tdir/ext2-mountpoint
3509         touch $DIR/$tdir/ext2-mountpoint/under_the_mount || error "touch failed"
3510         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint ||
3511                 error "mount failed for $EXT2_DEV $DIR/$tdir/ext2-mountpoint"
3512         ls $DIR/$tdir/ext2-mountpoint | grep "\<under_the_mount\>" && error
3513         cleanup_test32_mount
3514 }
3515 run_test 32q "stat follows mountpoints in Lustre (should return error)"
3516
3517 test_32r() {
3518         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3519
3520         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
3521         trap cleanup_test32_mount EXIT
3522         test_mkdir -p $DIR/$tdir/ext2-mountpoint
3523         touch $DIR/$tdir/ext2-mountpoint/under_the_mount || error "touch failed"
3524         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint ||
3525                 error "mount failed for $EXT2_DEV $DIR/$tdir/ext2-mountpoint"
3526         ls $DIR/$tdir/ext2-mountpoint | grep -q under_the_mount && error || true
3527         cleanup_test32_mount
3528 }
3529 run_test 32r "opendir follows mountpoints in Lustre (should return error)"
3530
3531 test_33aa() {
3532         rm -f $DIR/$tfile
3533         touch $DIR/$tfile
3534         chmod 444 $DIR/$tfile
3535         chown $RUNAS_ID $DIR/$tfile
3536         log 33_1
3537         $RUNAS $OPENFILE -f O_RDWR $DIR/$tfile && error || true
3538         log 33_2
3539 }
3540 run_test 33aa "write file with mode 444 (should return error)"
3541
3542 test_33a() {
3543         rm -fr $DIR/$tdir
3544         test_mkdir $DIR/$tdir
3545         chown $RUNAS_ID $DIR/$tdir
3546         $RUNAS $OPENFILE -f O_RDWR:O_CREAT -m 0444 $DIR/$tdir/$tfile ||
3547                 error "$RUNAS create $tdir/$tfile failed"
3548         $RUNAS $OPENFILE -f O_RDWR:O_CREAT -m 0444 $DIR/$tdir/$tfile &&
3549                 error "open RDWR" || true
3550 }
3551 run_test 33a "test open file(mode=0444) with O_RDWR (should return error)"
3552
3553 test_33b() {
3554         rm -fr $DIR/$tdir
3555         test_mkdir $DIR/$tdir
3556         chown $RUNAS_ID $DIR/$tdir
3557         $RUNAS $OPENFILE -f 1286739555 $DIR/$tdir/$tfile || true
3558 }
3559 run_test 33b "test open file with malformed flags (No panic)"
3560
3561 test_33c() {
3562         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3563         remote_ost_nodsh && skip "remote OST with nodsh"
3564
3565         local ostnum
3566         local ostname
3567         local write_bytes
3568         local all_zeros
3569
3570         all_zeros=:
3571         rm -fr $DIR/$tdir
3572         test_mkdir $DIR/$tdir
3573         # Read: 0, Write: 4, create/destroy: 2/0, stat: 1, punch: 0
3574
3575         sync
3576         for ostnum in $(seq $OSTCOUNT); do
3577                 # test-framework's OST numbering is one-based, while Lustre's
3578                 # is zero-based
3579                 ostname=$(printf "$FSNAME-OST%.4x" $((ostnum - 1)))
3580                 # Parsing llobdstat's output sucks; we could grep the /proc
3581                 # path, but that's likely to not be as portable as using the
3582                 # llobdstat utility.  So we parse lctl output instead.
3583                 write_bytes=$(do_facet ost$ostnum lctl get_param -n \
3584                         obdfilter/$ostname/stats |
3585                         awk '/^write_bytes/ {print $7}' )
3586                 echo "baseline_write_bytes@$OSTnum/$ostname=$write_bytes"
3587                 if (( ${write_bytes:-0} > 0 ))
3588                 then
3589                         all_zeros=false
3590                         break;
3591                 fi
3592         done
3593
3594         $all_zeros || return 0
3595
3596         # Write four bytes
3597         echo foo > $DIR/$tdir/bar
3598         # Really write them
3599         sync
3600
3601         # Total up write_bytes after writing.  We'd better find non-zeros.
3602         for ostnum in $(seq $OSTCOUNT); do
3603                 ostname=$(printf "$FSNAME-OST%.4x" $((ostnum - 1)))
3604                 write_bytes=$(do_facet ost$ostnum lctl get_param -n \
3605                         obdfilter/$ostname/stats |
3606                         awk '/^write_bytes/ {print $7}' )
3607                 echo "write_bytes@$OSTnum/$ostname=$write_bytes"
3608                 if (( ${write_bytes:-0} > 0 ))
3609                 then
3610                         all_zeros=false
3611                         break;
3612                 fi
3613         done
3614
3615         if $all_zeros
3616         then
3617                 for ostnum in $(seq $OSTCOUNT); do
3618                         ostname=$(printf "$FSNAME-OST%.4x" $((ostnum - 1)))
3619                         echo "Check that write_bytes is present in obdfilter/*/stats:"
3620                         do_facet ost$ostnum lctl get_param -n \
3621                                 obdfilter/$ostname/stats
3622                 done
3623                 error "OST not keeping write_bytes stats (b22312)"
3624         fi
3625 }
3626 run_test 33c "test llobdstat and write_bytes"
3627
3628 test_33d() {
3629         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 2 MDTs"
3630         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3631
3632         local MDTIDX=1
3633         local remote_dir=$DIR/$tdir/remote_dir
3634
3635         test_mkdir $DIR/$tdir
3636         $LFS mkdir -i $MDTIDX $remote_dir ||
3637                 error "create remote directory failed"
3638
3639         touch $remote_dir/$tfile
3640         chmod 444 $remote_dir/$tfile
3641         chown $RUNAS_ID $remote_dir/$tfile
3642
3643         $RUNAS $OPENFILE -f O_RDWR $DIR/$tfile && error || true
3644
3645         chown $RUNAS_ID $remote_dir
3646         $RUNAS $OPENFILE -f O_RDWR:O_CREAT -m 0444 $remote_dir/f33 ||
3647                                         error "create" || true
3648         $RUNAS $OPENFILE -f O_RDWR:O_CREAT -m 0444 $remote_dir/f33 &&
3649                                     error "open RDWR" || true
3650         $RUNAS $OPENFILE -f 1286739555 $remote_dir/f33 || true
3651 }
3652 run_test 33d "openfile with 444 modes and malformed flags under remote dir"
3653
3654 test_33e() {
3655         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
3656
3657         mkdir $DIR/$tdir
3658
3659         $LFS setdirstripe -i0 -c2 $DIR/$tdir/striped_dir
3660         $LFS setdirstripe -i1 -c2 $DIR/$tdir/striped_dir1
3661         mkdir $DIR/$tdir/local_dir
3662
3663         local s0_mode=$(stat -c%f $DIR/$tdir/striped_dir)
3664         local s1_mode=$(stat -c%f $DIR/$tdir/striped_dir1)
3665         local l_mode=$(stat -c%f $DIR/$tdir/local_dir)
3666
3667         [ "$l_mode" = "$s0_mode" -a "$l_mode" = "$s1_mode" ] ||
3668                 error "mkdir $l_mode striped0 $s0_mode striped1 $s1_mode"
3669
3670         rmdir $DIR/$tdir/* || error "rmdir failed"
3671
3672         umask 777
3673         $LFS setdirstripe -i0 -c2 $DIR/$tdir/striped_dir
3674         $LFS setdirstripe -i1 -c2 $DIR/$tdir/striped_dir1
3675         mkdir $DIR/$tdir/local_dir
3676
3677         s0_mode=$(stat -c%f $DIR/$tdir/striped_dir)
3678         s1_mode=$(stat -c%f $DIR/$tdir/striped_dir1)
3679         l_mode=$(stat -c%f $DIR/$tdir/local_dir)
3680
3681         [ "$l_mode" = "$s0_mode" -a "$l_mode" = "$s1_mode" ] ||
3682                 error "mkdir $l_mode striped0 $s0_mode striped1 $s1_mode 777"
3683
3684         rmdir $DIR/$tdir/* || error "rmdir(umask 777) failed"
3685
3686         umask 000
3687         $LFS setdirstripe -i0 -c2 $DIR/$tdir/striped_dir
3688         $LFS setdirstripe -i1 -c2 $DIR/$tdir/striped_dir1
3689         mkdir $DIR/$tdir/local_dir
3690
3691         s0_mode=$(stat -c%f $DIR/$tdir/striped_dir)
3692         s1_mode=$(stat -c%f $DIR/$tdir/striped_dir1)
3693         l_mode=$(stat -c%f $DIR/$tdir/local_dir)
3694
3695         [ "$l_mode" = "$s0_mode" -a "$l_mode" = "$s1_mode" ] ||
3696                 error "mkdir $l_mode striped0 $s0_mode striped1 $s1_mode 0"
3697 }
3698 run_test 33e "mkdir and striped directory should have same mode"
3699
3700 cleanup_33f() {
3701         trap 0
3702         do_facet $SINGLEMDS $LCTL set_param mdt.*.enable_remote_dir_gid=0
3703 }
3704
3705 test_33f() {
3706         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
3707         remote_mds_nodsh && skip "remote MDS with nodsh"
3708
3709         mkdir $DIR/$tdir
3710         chmod go+rwx $DIR/$tdir
3711         do_facet $SINGLEMDS $LCTL set_param mdt.*.enable_remote_dir_gid=-1
3712         trap cleanup_33f EXIT
3713
3714         $RUNAS lfs mkdir -i 0 -c$MDSCOUNT $DIR/$tdir/striped_dir ||
3715                 error "cannot create striped directory"
3716
3717         $RUNAS touch $DIR/$tdir/striped_dir/{0..16} ||
3718                 error "cannot create files in striped directory"
3719
3720         $RUNAS rm $DIR/$tdir/striped_dir/{0..16} ||
3721                 error "cannot remove files in striped directory"
3722
3723         $RUNAS rmdir $DIR/$tdir/striped_dir ||
3724                 error "cannot remove striped directory"
3725
3726         cleanup_33f
3727 }
3728 run_test 33f "nonroot user can create, access, and remove a striped directory"
3729
3730 test_33g() {
3731         mkdir -p $DIR/$tdir/dir2
3732
3733         local err=$($RUNAS mkdir $DIR/$tdir/dir2 2>&1)
3734         echo $err
3735         [[ $err =~ "exists" ]] || error "Not exists error"
3736 }
3737 run_test 33g "nonroot user create already existing root created file"
3738
3739 TEST_34_SIZE=${TEST_34_SIZE:-2000000000000}
3740 test_34a() {
3741         rm -f $DIR/f34
3742         $MCREATE $DIR/f34 || error "mcreate failed"
3743         $LFS getstripe $DIR/f34 2>&1 | grep -q "no stripe info" ||
3744                 error "getstripe failed"
3745         $TRUNCATE $DIR/f34 $TEST_34_SIZE || error "truncate failed"
3746         $LFS getstripe $DIR/f34 2>&1 | grep -q "no stripe info" ||
3747                 error "getstripe failed"
3748         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 ||
3749                 error "Size of $DIR/f34 not equal to $TEST_34_SIZE bytes"
3750 }
3751 run_test 34a "truncate file that has not been opened ==========="
3752
3753 test_34b() {
3754         [ ! -f $DIR/f34 ] && test_34a
3755         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 ||
3756                 error "Size of $DIR/f34 not equal to $TEST_34_SIZE bytes"
3757         $OPENFILE -f O_RDONLY $DIR/f34
3758         $LFS getstripe $DIR/f34 2>&1 | grep -q "no stripe info" ||
3759                 error "getstripe failed"
3760         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 ||
3761                 error "Size of $DIR/f34 not equal to $TEST_34_SIZE bytes"
3762 }
3763 run_test 34b "O_RDONLY opening file doesn't create objects ====="
3764
3765 test_34c() {
3766         [ ! -f $DIR/f34 ] && test_34a
3767         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 ||
3768                 error "Size of $DIR/f34 not equal to $TEST_34_SIZE bytes"
3769         $OPENFILE -f O_RDWR $DIR/f34
3770         $LFS getstripe $DIR/f34 2>&1 | grep -q "no stripe info" &&
3771                 error "$LFS getstripe failed"
3772         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 ||
3773                 error "Size of $DIR/f34 not equal to $TEST_34_SIZE bytes"
3774 }
3775 run_test 34c "O_RDWR opening file-with-size works =============="
3776
3777 test_34d() {
3778         [ ! -f $DIR/f34 ] && test_34a
3779         dd if=/dev/zero of=$DIR/f34 conv=notrunc bs=4k count=1 ||
3780                 error "dd failed"
3781         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 ||
3782                 error "Size of $DIR/f34 not equal to $TEST_34_SIZE bytes"
3783         rm $DIR/f34
3784 }
3785 run_test 34d "write to sparse file ============================="
3786
3787 test_34e() {
3788         rm -f $DIR/f34e
3789         $MCREATE $DIR/f34e || error "mcreate failed"
3790         $TRUNCATE $DIR/f34e 1000 || error "truncate failed"
3791         $CHECKSTAT -s 1000 $DIR/f34e ||
3792                 error "Size of $DIR/f34e not equal to 1000 bytes"
3793         $OPENFILE -f O_RDWR $DIR/f34e
3794         $CHECKSTAT -s 1000 $DIR/f34e ||
3795                 error "Size of $DIR/f34e not equal to 1000 bytes"
3796 }
3797 run_test 34e "create objects, some with size and some without =="
3798
3799 test_34f() { # bug 6242, 6243
3800         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3801
3802         SIZE34F=48000
3803         rm -f $DIR/f34f
3804         $MCREATE $DIR/f34f || error "mcreate failed"
3805         $TRUNCATE $DIR/f34f $SIZE34F || error "truncating $DIR/f3f to $SIZE34F"
3806         dd if=$DIR/f34f of=$TMP/f34f
3807         $CHECKSTAT -s $SIZE34F $TMP/f34f || error "$TMP/f34f not $SIZE34F bytes"
3808         dd if=/dev/zero of=$TMP/f34fzero bs=$SIZE34F count=1
3809         cmp $DIR/f34f $TMP/f34fzero || error "$DIR/f34f not all zero"
3810         cmp $TMP/f34f $TMP/f34fzero || error "$TMP/f34f not all zero"
3811         rm $TMP/f34f $TMP/f34fzero $DIR/f34f
3812 }
3813 run_test 34f "read from a file with no objects until EOF ======="
3814
3815 test_34g() {
3816         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3817
3818         dd if=/dev/zero of=$DIR/$tfile bs=1 count=100 seek=$TEST_34_SIZE ||
3819                 error "dd failed"
3820         $TRUNCATE $DIR/$tfile $((TEST_34_SIZE / 2))|| error "truncate failed"
3821         $CHECKSTAT -s $((TEST_34_SIZE / 2)) $DIR/$tfile ||
3822                 error "Size of $DIR/$tfile not equal to $((TEST_34_SIZE / 2))"
3823         cancel_lru_locks osc
3824         $CHECKSTAT -s $((TEST_34_SIZE / 2)) $DIR/$tfile ||
3825                 error "wrong size after lock cancel"
3826
3827         $TRUNCATE $DIR/$tfile $TEST_34_SIZE || error "truncate failed"
3828         $CHECKSTAT -s $TEST_34_SIZE $DIR/$tfile ||
3829                 error "expanding truncate failed"
3830         cancel_lru_locks osc
3831         $CHECKSTAT -s $TEST_34_SIZE $DIR/$tfile ||
3832                 error "wrong expanded size after lock cancel"
3833 }
3834 run_test 34g "truncate long file ==============================="
3835
3836 test_34h() {
3837         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3838
3839         local gid=10
3840         local sz=1000
3841
3842         dd if=/dev/zero of=$DIR/$tfile bs=1M count=10 || error "dd failed"
3843         sync # Flush the cache so that multiop below does not block on cache
3844              # flush when getting the group lock
3845         $MULTIOP $DIR/$tfile OG${gid}T${sz}g${gid}c &
3846         MULTIPID=$!
3847
3848         # Since just timed wait is not good enough, let's do a sync write
3849         # that way we are sure enough time for a roundtrip + processing
3850         # passed + 2 seconds of extra margin.
3851         dd if=/dev/zero of=$DIR/${tfile}-1 bs=$PAGE_SIZE oflag=direct count=1
3852         rm $DIR/${tfile}-1
3853         sleep 2
3854
3855         if [[ `ps h -o comm -p $MULTIPID` == "multiop" ]]; then
3856                 error "Multiop blocked on ftruncate, pid=$MULTIPID"
3857                 kill -9 $MULTIPID
3858         fi
3859         wait $MULTIPID
3860         local nsz=`stat -c %s $DIR/$tfile`
3861         [[ $nsz == $sz ]] || error "New size wrong $nsz != $sz"
3862 }
3863 run_test 34h "ftruncate file under grouplock should not block"
3864
3865 test_35a() {
3866         cp /bin/sh $DIR/f35a
3867         chmod 444 $DIR/f35a
3868         chown $RUNAS_ID $DIR/f35a
3869         $RUNAS $DIR/f35a && error || true
3870         rm $DIR/f35a
3871 }
3872 run_test 35a "exec file with mode 444 (should return and not leak)"
3873
3874 test_36a() {
3875         rm -f $DIR/f36
3876         utime $DIR/f36 || error "utime failed for MDS"
3877 }
3878 run_test 36a "MDS utime check (mknod, utime)"
3879
3880 test_36b() {
3881         echo "" > $DIR/f36
3882         utime $DIR/f36 || error "utime failed for OST"
3883 }
3884 run_test 36b "OST utime check (open, utime)"
3885
3886 test_36c() {
3887         rm -f $DIR/d36/f36
3888         test_mkdir $DIR/d36
3889         chown $RUNAS_ID $DIR/d36
3890         $RUNAS utime $DIR/d36/f36 || error "utime failed for MDS as non-root"
3891 }
3892 run_test 36c "non-root MDS utime check (mknod, utime)"
3893
3894 test_36d() {
3895         [ ! -d $DIR/d36 ] && test_36c
3896         echo "" > $DIR/d36/f36
3897         $RUNAS utime $DIR/d36/f36 || error "utime failed for OST as non-root"
3898 }
3899 run_test 36d "non-root OST utime check (open, utime)"
3900
3901 test_36e() {
3902         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID -- skipping"
3903
3904         test_mkdir $DIR/$tdir
3905         touch $DIR/$tdir/$tfile
3906         $RUNAS utime $DIR/$tdir/$tfile &&
3907                 error "utime worked, expected failure" || true
3908 }
3909 run_test 36e "utime on non-owned file (should return error)"
3910
3911 subr_36fh() {
3912         local fl="$1"
3913         local LANG_SAVE=$LANG
3914         local LC_LANG_SAVE=$LC_LANG
3915         export LANG=C LC_LANG=C # for date language
3916
3917         DATESTR="Dec 20  2000"
3918         test_mkdir $DIR/$tdir
3919         lctl set_param fail_loc=$fl
3920         date; date +%s
3921         cp /etc/hosts $DIR/$tdir/$tfile
3922         sync & # write RPC generated with "current" inode timestamp, but delayed
3923         sleep 1
3924         touch --date="$DATESTR" $DIR/$tdir/$tfile # setattr timestamp in past
3925         LS_BEFORE="`ls -l $DIR/$tdir/$tfile`" # old timestamp from client cache
3926         cancel_lru_locks $OSC
3927         LS_AFTER="`ls -l $DIR/$tdir/$tfile`"  # timestamp from OST object
3928         date; date +%s
3929         [ "$LS_BEFORE" != "$LS_AFTER" ] && \
3930                 echo "BEFORE: $LS_BEFORE" && \
3931                 echo "AFTER : $LS_AFTER" && \
3932                 echo "WANT  : $DATESTR" && \
3933                 error "$DIR/$tdir/$tfile timestamps changed" || true
3934
3935         export LANG=$LANG_SAVE LC_LANG=$LC_LANG_SAVE
3936 }
3937
3938 test_36f() {
3939         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3940
3941         #define OBD_FAIL_OST_BRW_PAUSE_BULK 0x214
3942         subr_36fh "0x80000214"
3943 }
3944 run_test 36f "utime on file racing with OST BRW write =========="
3945
3946 test_36g() {
3947         remote_ost_nodsh && skip "remote OST with nodsh"
3948         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3949         [ $MDS1_VERSION -lt $(version_code 2.12.51) ] &&
3950                 skip "Need MDS version at least 2.12.51"
3951
3952         local fmd_max_age
3953         local fmd
3954         local facet="ost1"
3955         local tgt="obdfilter"
3956
3957         [[ $OSC == "mdc" ]] && tgt="mdt" && facet="mds1"
3958
3959         test_mkdir $DIR/$tdir
3960         fmd_max_age=$(do_facet $facet \
3961                 "lctl get_param -n $tgt.*.tgt_fmd_seconds 2> /dev/null | \
3962                 head -n 1")
3963
3964         echo "FMD max age: ${fmd_max_age}s"
3965         touch $DIR/$tdir/$tfile
3966         fmd=$(do_facet $facet "lctl get_param -n $tgt.*.exports.*.fmd_count" |
3967                 gawk '{cnt=cnt+$1}  END{print cnt}')
3968         echo "FMD before: $fmd"
3969         [[ $fmd == 0 ]] &&
3970                 error "FMD wasn't create by touch"
3971         sleep $((fmd_max_age + 12))
3972         fmd=$(do_facet $facet "lctl get_param -n $tgt.*.exports.*.fmd_count" |
3973                 gawk '{cnt=cnt+$1}  END{print cnt}')
3974         echo "FMD after: $fmd"
3975         [[ $fmd == 0 ]] ||
3976                 error "FMD wasn't expired by ping"
3977 }
3978 run_test 36g "FMD cache expiry ====================="
3979
3980 test_36h() {
3981         [ $PARALLEL == "yes" ] && skip "skip parallel run"
3982
3983         #define OBD_FAIL_OST_BRW_PAUSE_BULK2 0x227
3984         subr_36fh "0x80000227"
3985 }
3986 run_test 36h "utime on file racing with OST BRW write =========="
3987
3988 test_36i() {
3989         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
3990
3991         test_mkdir $DIR/$tdir
3992         $LFS setdirstripe -i0 -c$MDSCOUNT $DIR/$tdir/striped_dir
3993
3994         local mtime=$(stat -c%Y $DIR/$tdir/striped_dir)
3995         local new_mtime=$((mtime + 200))
3996
3997         #change Modify time of striped dir
3998         touch -m -d @$new_mtime $DIR/$tdir/striped_dir ||
3999                         error "change mtime failed"
4000
4001         local got=$(stat -c%Y $DIR/$tdir/striped_dir)
4002
4003         [ "$new_mtime" = "$got" ] || error "expect $new_mtime got $got"
4004 }
4005 run_test 36i "change mtime on striped directory"
4006
4007 # test_37 - duplicate with tests 32q 32r
4008
4009 test_38() {
4010         local file=$DIR/$tfile
4011         touch $file
4012         openfile -f O_DIRECTORY $file
4013         local RC=$?
4014         local ENOTDIR=20
4015         [ $RC -eq 0 ] && error "opened file $file with O_DIRECTORY" || true
4016         [ $RC -eq $ENOTDIR ] || error "error $RC should be ENOTDIR ($ENOTDIR)"
4017 }
4018 run_test 38 "open a regular file with O_DIRECTORY should return -ENOTDIR ==="
4019
4020 test_39a() { # was test_39
4021         touch $DIR/$tfile
4022         touch $DIR/${tfile}2
4023 #       ls -l  $DIR/$tfile $DIR/${tfile}2
4024 #       ls -lu  $DIR/$tfile $DIR/${tfile}2
4025 #       ls -lc  $DIR/$tfile $DIR/${tfile}2
4026         sleep 2
4027         $OPENFILE -f O_CREAT:O_TRUNC:O_WRONLY $DIR/${tfile}2
4028         if [ ! $DIR/${tfile}2 -nt $DIR/$tfile ]; then
4029                 echo "mtime"
4030                 ls -l --full-time $DIR/$tfile $DIR/${tfile}2
4031                 echo "atime"
4032                 ls -lu --full-time $DIR/$tfile $DIR/${tfile}2
4033                 echo "ctime"
4034                 ls -lc --full-time $DIR/$tfile $DIR/${tfile}2
4035                 error "O_TRUNC didn't change timestamps"
4036         fi
4037 }
4038 run_test 39a "mtime changed on create"
4039
4040 test_39b() {
4041         test_mkdir -c1 $DIR/$tdir
4042         cp -p /etc/passwd $DIR/$tdir/fopen
4043         cp -p /etc/passwd $DIR/$tdir/flink
4044         cp -p /etc/passwd $DIR/$tdir/funlink
4045         cp -p /etc/passwd $DIR/$tdir/frename
4046         ln $DIR/$tdir/funlink $DIR/$tdir/funlink2
4047
4048         sleep 1
4049         echo "aaaaaa" >> $DIR/$tdir/fopen
4050         echo "aaaaaa" >> $DIR/$tdir/flink
4051         echo "aaaaaa" >> $DIR/$tdir/funlink
4052         echo "aaaaaa" >> $DIR/$tdir/frename
4053
4054         local open_new=`stat -c %Y $DIR/$tdir/fopen`
4055         local link_new=`stat -c %Y $DIR/$tdir/flink`
4056         local unlink_new=`stat -c %Y $DIR/$tdir/funlink`
4057         local rename_new=`stat -c %Y $DIR/$tdir/frename`
4058
4059         cat $DIR/$tdir/fopen > /dev/null
4060         ln $DIR/$tdir/flink $DIR/$tdir/flink2
4061         rm -f $DIR/$tdir/funlink2
4062         mv -f $DIR/$tdir/frename $DIR/$tdir/frename2
4063
4064         for (( i=0; i < 2; i++ )) ; do
4065                 local open_new2=`stat -c %Y $DIR/$tdir/fopen`
4066                 local link_new2=`stat -c %Y $DIR/$tdir/flink`
4067                 local unlink_new2=`stat -c %Y $DIR/$tdir/funlink`
4068                 local rename_new2=`stat -c %Y $DIR/$tdir/frename2`
4069
4070                 [ $open_new2 -eq $open_new ] || error "open file reverses mtime"
4071                 [ $link_new2 -eq $link_new ] || error "link file reverses mtime"
4072                 [ $unlink_new2 -eq $unlink_new ] || error "unlink file reverses mtime"
4073                 [ $rename_new2 -eq $rename_new ] || error "rename file reverses mtime"
4074
4075                 cancel_lru_locks $OSC
4076                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4077         done
4078 }
4079 run_test 39b "mtime change on open, link, unlink, rename  ======"
4080
4081 # this should be set to past
4082 TEST_39_MTIME=`date -d "1 year ago" +%s`
4083
4084 # bug 11063
4085 test_39c() {
4086         touch $DIR1/$tfile
4087         sleep 2
4088         local mtime0=`stat -c %Y $DIR1/$tfile`
4089
4090         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
4091         local mtime1=`stat -c %Y $DIR1/$tfile`
4092         [ "$mtime1" = $TEST_39_MTIME ] || \
4093                 error "mtime is not set to past: $mtime1, should be $TEST_39_MTIME"
4094
4095         local d1=`date +%s`
4096         echo hello >> $DIR1/$tfile
4097         local d2=`date +%s`
4098         local mtime2=`stat -c %Y $DIR1/$tfile`
4099         [ "$mtime2" -ge "$d1" ] && [ "$mtime2" -le "$d2" ] || \
4100                 error "mtime is not updated on write: $d1 <= $mtime2 <= $d2"
4101
4102         mv $DIR1/$tfile $DIR1/$tfile-1
4103
4104         for (( i=0; i < 2; i++ )) ; do
4105                 local mtime3=`stat -c %Y $DIR1/$tfile-1`
4106                 [ "$mtime2" = "$mtime3" ] || \
4107                         error "mtime ($mtime2) changed (to $mtime3) on rename"
4108
4109                 cancel_lru_locks $OSC
4110                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4111         done
4112 }
4113 run_test 39c "mtime change on rename ==========================="
4114
4115 # bug 21114
4116 test_39d() {
4117         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4118
4119         touch $DIR1/$tfile
4120         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
4121
4122         for (( i=0; i < 2; i++ )) ; do
4123                 local mtime=`stat -c %Y $DIR1/$tfile`
4124                 [ $mtime = $TEST_39_MTIME ] || \
4125                         error "mtime($mtime) is not set to $TEST_39_MTIME"
4126
4127                 cancel_lru_locks $OSC
4128                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4129         done
4130 }
4131 run_test 39d "create, utime, stat =============================="
4132
4133 # bug 21114
4134 test_39e() {
4135         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4136
4137         touch $DIR1/$tfile
4138         local mtime1=`stat -c %Y $DIR1/$tfile`
4139
4140         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
4141
4142         for (( i=0; i < 2; i++ )) ; do
4143                 local mtime2=`stat -c %Y $DIR1/$tfile`
4144                 [ $mtime2 = $TEST_39_MTIME ] || \
4145                         error "mtime($mtime2) is not set to $TEST_39_MTIME"
4146
4147                 cancel_lru_locks $OSC
4148                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4149         done
4150 }
4151 run_test 39e "create, stat, utime, stat ========================"
4152
4153 # bug 21114
4154 test_39f() {
4155         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4156
4157         touch $DIR1/$tfile
4158         mtime1=`stat -c %Y $DIR1/$tfile`
4159
4160         sleep 2
4161         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
4162
4163         for (( i=0; i < 2; i++ )) ; do
4164                 local mtime2=`stat -c %Y $DIR1/$tfile`
4165                 [ $mtime2 = $TEST_39_MTIME ] || \
4166                         error "mtime($mtime2) is not set to $TEST_39_MTIME"
4167
4168                 cancel_lru_locks $OSC
4169                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4170         done
4171 }
4172 run_test 39f "create, stat, sleep, utime, stat ================="
4173
4174 # bug 11063
4175 test_39g() {
4176         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4177
4178         echo hello >> $DIR1/$tfile
4179         local mtime1=`stat -c %Y $DIR1/$tfile`
4180
4181         sleep 2
4182         chmod o+r $DIR1/$tfile
4183
4184         for (( i=0; i < 2; i++ )) ; do
4185                 local mtime2=`stat -c %Y $DIR1/$tfile`
4186                 [ "$mtime1" = "$mtime2" ] || \
4187                         error "lost mtime: $mtime2, should be $mtime1"
4188
4189                 cancel_lru_locks $OSC
4190                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4191         done
4192 }
4193 run_test 39g "write, chmod, stat ==============================="
4194
4195 # bug 11063
4196 test_39h() {
4197         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4198
4199         touch $DIR1/$tfile
4200         sleep 1
4201
4202         local d1=`date`
4203         echo hello >> $DIR1/$tfile
4204         local mtime1=`stat -c %Y $DIR1/$tfile`
4205
4206         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
4207         local d2=`date`
4208         if [ "$d1" != "$d2" ]; then
4209                 echo "write and touch not within one second"
4210         else
4211                 for (( i=0; i < 2; i++ )) ; do
4212                         local mtime2=`stat -c %Y $DIR1/$tfile`
4213                         [ "$mtime2" = $TEST_39_MTIME ] || \
4214                                 error "lost mtime: $mtime2, should be $TEST_39_MTIME"
4215
4216                         cancel_lru_locks $OSC
4217                         if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4218                 done
4219         fi
4220 }
4221 run_test 39h "write, utime within one second, stat ============="
4222
4223 test_39i() {
4224         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4225
4226         touch $DIR1/$tfile
4227         sleep 1
4228
4229         echo hello >> $DIR1/$tfile
4230         local mtime1=`stat -c %Y $DIR1/$tfile`
4231
4232         mv $DIR1/$tfile $DIR1/$tfile-1
4233
4234         for (( i=0; i < 2; i++ )) ; do
4235                 local mtime2=`stat -c %Y $DIR1/$tfile-1`
4236
4237                 [ "$mtime1" = "$mtime2" ] || \
4238                         error "lost mtime: $mtime2, should be $mtime1"
4239
4240                 cancel_lru_locks $OSC
4241                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4242         done
4243 }
4244 run_test 39i "write, rename, stat =============================="
4245
4246 test_39j() {
4247         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4248
4249         start_full_debug_logging
4250         touch $DIR1/$tfile
4251         sleep 1
4252
4253         #define OBD_FAIL_OSC_DELAY_SETTIME       0x412
4254         lctl set_param fail_loc=0x80000412
4255         multiop_bg_pause $DIR1/$tfile oO_RDWR:w2097152_c ||
4256                 error "multiop failed"
4257         local multipid=$!
4258         local mtime1=`stat -c %Y $DIR1/$tfile`
4259
4260         mv $DIR1/$tfile $DIR1/$tfile-1
4261
4262         kill -USR1 $multipid
4263         wait $multipid || error "multiop close failed"
4264
4265         for (( i=0; i < 2; i++ )) ; do
4266                 local mtime2=`stat -c %Y $DIR1/$tfile-1`
4267                 [ "$mtime1" = "$mtime2" ] ||
4268                         error "mtime is lost on close: $mtime2, " \
4269                               "should be $mtime1"
4270
4271                 cancel_lru_locks
4272                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4273         done
4274         lctl set_param fail_loc=0
4275         stop_full_debug_logging
4276 }
4277 run_test 39j "write, rename, close, stat ======================="
4278
4279 test_39k() {
4280         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4281
4282         touch $DIR1/$tfile
4283         sleep 1
4284
4285         multiop_bg_pause $DIR1/$tfile oO_RDWR:w2097152_c || error "multiop failed"
4286         local multipid=$!
4287         local mtime1=`stat -c %Y $DIR1/$tfile`
4288
4289         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
4290
4291         kill -USR1 $multipid
4292         wait $multipid || error "multiop close failed"
4293
4294         for (( i=0; i < 2; i++ )) ; do
4295                 local mtime2=`stat -c %Y $DIR1/$tfile`
4296
4297                 [ "$mtime2" = $TEST_39_MTIME ] || \
4298                         error "mtime is lost on close: $mtime2, should be $TEST_39_MTIME"
4299
4300                 cancel_lru_locks
4301                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4302         done
4303 }
4304 run_test 39k "write, utime, close, stat ========================"
4305
4306 # this should be set to future
4307 TEST_39_ATIME=`date -d "1 year" +%s`
4308
4309 test_39l() {
4310         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4311         remote_mds_nodsh && skip "remote MDS with nodsh"
4312
4313         local atime_diff=$(do_facet $SINGLEMDS \
4314                                 lctl get_param -n mdd.*MDT0000*.atime_diff)
4315         rm -rf $DIR/$tdir
4316         mkdir -p $DIR/$tdir
4317
4318         # test setting directory atime to future
4319         touch -a -d @$TEST_39_ATIME $DIR/$tdir
4320         local atime=$(stat -c %X $DIR/$tdir)
4321         [ "$atime" = $TEST_39_ATIME ] ||
4322                 error "atime is not set to future: $atime, $TEST_39_ATIME"
4323
4324         # test setting directory atime from future to now
4325         local now=$(date +%s)
4326         touch -a -d @$now $DIR/$tdir
4327
4328         atime=$(stat -c %X $DIR/$tdir)
4329         [ "$atime" -eq "$now"  ] ||
4330                 error "atime is not updated from future: $atime, $now"
4331
4332         do_facet $SINGLEMDS lctl set_param -n mdd.*MDT0000*.atime_diff=2
4333         sleep 3
4334
4335         # test setting directory atime when now > dir atime + atime_diff
4336         local d1=$(date +%s)
4337         ls $DIR/$tdir
4338         local d2=$(date +%s)
4339         cancel_lru_locks mdc
4340         atime=$(stat -c %X $DIR/$tdir)
4341         [ "$atime" -ge "$d1" -a "$atime" -le "$d2" ] ||
4342                 error "atime is not updated  : $atime, should be $d2"
4343
4344         do_facet $SINGLEMDS lctl set_param -n mdd.*MDT0000*.atime_diff=60
4345         sleep 3
4346
4347         # test not setting directory atime when now < dir atime + atime_diff
4348         ls $DIR/$tdir
4349         cancel_lru_locks mdc
4350         atime=$(stat -c %X $DIR/$tdir)
4351         [ "$atime" -ge "$d1" -a "$atime" -le "$d2" ] ||
4352                 error "atime is updated to $atime, should remain $d1<atime<$d2"
4353
4354         do_facet $SINGLEMDS \
4355                 lctl set_param -n mdd.*MDT0000*.atime_diff=$atime_diff
4356 }
4357 run_test 39l "directory atime update ==========================="
4358
4359 test_39m() {
4360         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4361
4362         touch $DIR1/$tfile
4363         sleep 2
4364         local far_past_mtime=$(date -d "May 29 1953" +%s)
4365         local far_past_atime=$(date -d "Dec 17 1903" +%s)
4366
4367         touch -m -d @$far_past_mtime $DIR1/$tfile
4368         touch -a -d @$far_past_atime $DIR1/$tfile
4369
4370         for (( i=0; i < 2; i++ )) ; do
4371                 local timestamps=$(stat -c "%X %Y" $DIR1/$tfile)
4372                 [ "$timestamps" = "$far_past_atime $far_past_mtime" ] || \
4373                         error "atime or mtime set incorrectly"
4374
4375                 cancel_lru_locks $OSC
4376                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
4377         done
4378 }
4379 run_test 39m "test atime and mtime before 1970"
4380
4381 test_39n() { # LU-3832
4382         remote_mds_nodsh && skip "remote MDS with nodsh"
4383
4384         local atime_diff=$(do_facet $SINGLEMDS \
4385                 lctl get_param -n mdd.*MDT0000*.atime_diff)
4386         local atime0
4387         local atime1
4388         local atime2
4389
4390         do_facet $SINGLEMDS lctl set_param -n mdd.*MDT0000*.atime_diff=1
4391
4392         rm -rf $DIR/$tfile
4393         dd if=/dev/zero of=$DIR/$tfile bs=4096 count=1 status=noxfer
4394         atime0=$(stat -c %X $DIR/$tfile)
4395
4396         sleep 5
4397         $MULTIOP $DIR/$tfile oO_RDONLY:O_NOATIME:r4096c
4398         atime1=$(stat -c %X $DIR/$tfile)
4399
4400         sleep 5
4401         cancel_lru_locks mdc
4402         cancel_lru_locks osc
4403         $MULTIOP $DIR/$tfile oO_RDONLY:O_NOATIME:r4096c
4404         atime2=$(stat -c %X $DIR/$tfile)
4405
4406         do_facet $SINGLEMDS \
4407                 lctl set_param -n mdd.*MDT0000*.atime_diff=$atime_diff
4408
4409         [ "$atime0" -eq "$atime1" ] || error "atime0 $atime0 != atime1 $atime1"
4410         [ "$atime1" -eq "$atime2" ] || error "atime0 $atime0 != atime1 $atime1"
4411 }
4412 run_test 39n "check that O_NOATIME is honored"
4413
4414 test_39o() {
4415         TESTDIR=$DIR/$tdir/$tfile
4416         [ -e $TESTDIR ] && rm -rf $TESTDIR
4417         mkdir -p $TESTDIR
4418         cd $TESTDIR
4419         links1=2
4420         ls
4421         mkdir a b
4422         ls
4423         links2=$(stat -c %h .)
4424         [ $(($links1 + 2)) != $links2 ] &&
4425                 error "wrong links count $(($links1 + 2)) != $links2"
4426         rmdir b
4427         links3=$(stat -c %h .)
4428         [ $(($links1 + 1)) != $links3 ] &&
4429                 error "wrong links count $links1 != $links3"
4430         return 0
4431 }
4432 run_test 39o "directory cached attributes updated after create"
4433
4434 test_39p() {
4435         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 2 MDTs"
4436
4437         local MDTIDX=1
4438         TESTDIR=$DIR/$tdir/$tdir
4439         [ -e $TESTDIR ] && rm -rf $TESTDIR
4440         test_mkdir -p $TESTDIR
4441         cd $TESTDIR
4442         links1=2
4443         ls
4444         test_mkdir -i $MDTIDX $TESTDIR/remote_dir1
4445         test_mkdir -i $MDTIDX $TESTDIR/remote_dir2
4446         ls
4447         links2=$(stat -c %h .)
4448         [ $(($links1 + 2)) != $links2 ] &&
4449                 error "wrong links count $(($links1 + 2)) != $links2"
4450         rmdir remote_dir2
4451         links3=$(stat -c %h .)
4452         [ $(($links1 + 1)) != $links3 ] &&
4453                 error "wrong links count $links1 != $links3"
4454         return 0
4455 }
4456 run_test 39p "remote directory cached attributes updated after create ========"
4457
4458
4459 test_39q() { # LU-8041
4460         local testdir=$DIR/$tdir
4461         mkdir -p $testdir
4462         multiop_bg_pause $testdir D_c || error "multiop failed"
4463         local multipid=$!
4464         cancel_lru_locks mdc
4465         kill -USR1 $multipid
4466         local atime=$(stat -c %X $testdir)
4467         [ "$atime" -ne 0 ] || error "atime is zero"
4468 }
4469 run_test 39q "close won't zero out atime"
4470
4471 test_40() {
4472         dd if=/dev/zero of=$DIR/$tfile bs=4096 count=1
4473         $RUNAS $OPENFILE -f O_WRONLY:O_TRUNC $DIR/$tfile &&
4474                 error "openfile O_WRONLY:O_TRUNC $tfile failed"
4475         $CHECKSTAT -t file -s 4096 $DIR/$tfile ||
4476                 error "$tfile is not 4096 bytes in size"
4477 }
4478 run_test 40 "failed open(O_TRUNC) doesn't truncate ============="
4479
4480 test_41() {
4481         # bug 1553
4482         small_write $DIR/f41 18
4483 }
4484 run_test 41 "test small file write + fstat ====================="
4485
4486 count_ost_writes() {
4487         lctl get_param -n ${OSC}.*.stats |
4488                 awk -vwrites=0 '/ost_write/ { writes += $2 } \
4489                         END { printf("%0.0f", writes) }'
4490 }
4491
4492 # decent default
4493 WRITEBACK_SAVE=500
4494 DIRTY_RATIO_SAVE=40
4495 MAX_DIRTY_RATIO=50
4496 BG_DIRTY_RATIO_SAVE=10
4497 MAX_BG_DIRTY_RATIO=25
4498
4499 start_writeback() {
4500         trap 0
4501         # in 2.6, restore /proc/sys/vm/dirty_writeback_centisecs,
4502         # dirty_ratio, dirty_background_ratio
4503         if [ -f /proc/sys/vm/dirty_writeback_centisecs ]; then
4504                 sysctl -w vm.dirty_writeback_centisecs=$WRITEBACK_SAVE
4505                 sysctl -w vm.dirty_background_ratio=$BG_DIRTY_RATIO_SAVE
4506                 sysctl -w vm.dirty_ratio=$DIRTY_RATIO_SAVE
4507         else
4508                 # if file not here, we are a 2.4 kernel
4509                 kill -CONT `pidof kupdated`
4510         fi
4511 }
4512
4513 stop_writeback() {
4514         # setup the trap first, so someone cannot exit the test at the
4515         # exact wrong time and mess up a machine
4516         trap start_writeback EXIT
4517         # in 2.6, save and 0 /proc/sys/vm/dirty_writeback_centisecs
4518         if [ -f /proc/sys/vm/dirty_writeback_centisecs ]; then
4519                 WRITEBACK_SAVE=`sysctl -n vm.dirty_writeback_centisecs`
4520                 sysctl -w vm.dirty_writeback_centisecs=0
4521                 sysctl -w vm.dirty_writeback_centisecs=0
4522                 # save and increase /proc/sys/vm/dirty_ratio
4523                 DIRTY_RATIO_SAVE=`sysctl -n vm.dirty_ratio`
4524                 sysctl -w vm.dirty_ratio=$MAX_DIRTY_RATIO
4525                 # save and increase /proc/sys/vm/dirty_background_ratio
4526                 BG_DIRTY_RATIO_SAVE=`sysctl -n vm.dirty_background_ratio`
4527                 sysctl -w vm.dirty_background_ratio=$MAX_BG_DIRTY_RATIO
4528         else
4529                 # if file not here, we are a 2.4 kernel
4530                 kill -STOP `pidof kupdated`
4531         fi
4532 }
4533
4534 # ensure that all stripes have some grant before we test client-side cache
4535 setup_test42() {
4536         for i in `seq -f $DIR/f42-%g 1 $OSTCOUNT`; do
4537                 dd if=/dev/zero of=$i bs=4k count=1
4538                 rm $i
4539         done
4540 }
4541
4542 # Tests 42* verify that our behaviour is correct WRT caching, file closure,
4543 # file truncation, and file removal.
4544 test_42a() {
4545         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4546
4547         setup_test42
4548         cancel_lru_locks $OSC
4549         stop_writeback
4550         sync; sleep 1; sync # just to be safe
4551         BEFOREWRITES=`count_ost_writes`
4552         lctl get_param -n osc.*[oO][sS][cC][_-]*.cur_grant_bytes | grep "[0-9]"
4553         dd if=/dev/zero of=$DIR/f42a bs=1024 count=100
4554         AFTERWRITES=`count_ost_writes`
4555         [ $BEFOREWRITES -eq $AFTERWRITES ] || \
4556                 error "$BEFOREWRITES < $AFTERWRITES"
4557         start_writeback
4558 }
4559 run_test 42a "ensure that we don't flush on close"
4560
4561 test_42b() {
4562         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4563
4564         setup_test42
4565         cancel_lru_locks $OSC
4566         stop_writeback
4567         sync
4568         dd if=/dev/zero of=$DIR/f42b bs=1024 count=100
4569         BEFOREWRITES=$(count_ost_writes)
4570         $MUNLINK $DIR/f42b || error "$MUNLINK $DIR/f42b: $?"
4571         AFTERWRITES=$(count_ost_writes)
4572         if [[ $BEFOREWRITES -lt $AFTERWRITES ]]; then
4573                 error "$BEFOREWRITES < $AFTERWRITES on unlink"
4574         fi
4575         BEFOREWRITES=$(count_ost_writes)
4576         sync || error "sync: $?"
4577         AFTERWRITES=$(count_ost_writes)
4578         if [[ $BEFOREWRITES -lt $AFTERWRITES ]]; then
4579                 error "$BEFOREWRITES < $AFTERWRITES on sync"
4580         fi
4581         dmesg | grep 'error from obd_brw_async' && error 'error writing back'
4582         start_writeback
4583         return 0
4584 }
4585 run_test 42b "test destroy of file with cached dirty data ======"
4586
4587 # if these tests just want to test the effect of truncation,
4588 # they have to be very careful.  consider:
4589 # - the first open gets a {0,EOF}PR lock
4590 # - the first write conflicts and gets a {0, count-1}PW
4591 # - the rest of the writes are under {count,EOF}PW
4592 # - the open for truncate tries to match a {0,EOF}PR
4593 #   for the filesize and cancels the PWs.
4594 # any number of fixes (don't get {0,EOF} on open, match
4595 # composite locks, do smarter file size management) fix
4596 # this, but for now we want these tests to verify that
4597 # the cancellation with truncate intent works, so we
4598 # start the file with a full-file pw lock to match against
4599 # until the truncate.
4600 trunc_test() {
4601         test=$1
4602         file=$DIR/$test
4603         offset=$2
4604         cancel_lru_locks $OSC
4605         stop_writeback
4606         # prime the file with 0,EOF PW to match
4607         touch $file
4608         $TRUNCATE $file 0
4609         sync; sync
4610         # now the real test..
4611         dd if=/dev/zero of=$file bs=1024 count=100
4612         BEFOREWRITES=`count_ost_writes`
4613         $TRUNCATE $file $offset
4614         cancel_lru_locks $OSC
4615         AFTERWRITES=`count_ost_writes`
4616         start_writeback
4617 }
4618
4619 test_42c() {
4620         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4621
4622         trunc_test 42c 1024
4623         [ $BEFOREWRITES -eq $AFTERWRITES ] &&
4624                 error "beforewrites $BEFOREWRITES == afterwrites $AFTERWRITES on truncate"
4625         rm $file
4626 }
4627 run_test 42c "test partial truncate of file with cached dirty data"
4628
4629 test_42d() {
4630         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4631
4632         trunc_test 42d 0
4633         [ $BEFOREWRITES -eq $AFTERWRITES ] ||
4634                 error "beforewrites $BEFOREWRITES != afterwrites $AFTERWRITES on truncate"
4635         rm $file
4636 }
4637 run_test 42d "test complete truncate of file with cached dirty data"
4638
4639 test_42e() { # bug22074
4640         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4641
4642         local TDIR=$DIR/${tdir}e
4643         local pages=16 # hardcoded 16 pages, don't change it.
4644         local files=$((OSTCOUNT * 500)) # hopefully 500 files on each OST
4645         local proc_osc0="osc.${FSNAME}-OST0000-osc-[^MDT]*"
4646         local max_dirty_mb
4647         local warmup_files
4648
4649         test_mkdir $DIR/${tdir}e
4650         $LFS setstripe -c 1 $TDIR
4651         createmany -o $TDIR/f $files
4652
4653         max_dirty_mb=$($LCTL get_param -n $proc_osc0/max_dirty_mb)
4654
4655         # we assume that with $OSTCOUNT files, at least one of them will
4656         # be allocated on OST0.
4657         warmup_files=$((OSTCOUNT * max_dirty_mb))
4658         createmany -o $TDIR/w $warmup_files
4659
4660         # write a large amount of data into one file and sync, to get good
4661         # avail_grant number from OST.
4662         for ((i=0; i<$warmup_files; i++)); do
4663                 idx=$($LFS getstripe -i $TDIR/w$i)
4664                 [ $idx -ne 0 ] && continue
4665                 dd if=/dev/zero of=$TDIR/w$i bs="$max_dirty_mb"M count=1
4666                 break
4667         done
4668         [[ $i -gt $warmup_files ]] && error "OST0 is still cold"
4669         sync
4670         $LCTL get_param $proc_osc0/cur_dirty_bytes
4671         $LCTL get_param $proc_osc0/cur_grant_bytes
4672
4673         # create as much dirty pages as we can while not to trigger the actual
4674         # RPCs directly. but depends on the env, VFS may trigger flush during this
4675         # period, hopefully we are good.
4676         for ((i=0; i<$warmup_files; i++)); do
4677                 idx=$($LFS getstripe -i $TDIR/w$i)
4678                 [ $idx -ne 0 ] && continue
4679                 dd if=/dev/zero of=$TDIR/w$i bs=1M count=1 2>/dev/null
4680         done
4681         $LCTL get_param $proc_osc0/cur_dirty_bytes
4682         $LCTL get_param $proc_osc0/cur_grant_bytes
4683
4684         # perform the real test
4685         $LCTL set_param $proc_osc0/rpc_stats 0
4686         for ((;i<$files; i++)); do
4687                 [ $($LFS getstripe -i $TDIR/f$i) -eq 0 ] || continue
4688                 dd if=/dev/zero of=$TDIR/f$i bs=$PAGE_SIZE count=$pages 2>/dev/null
4689         done
4690         sync
4691         $LCTL get_param $proc_osc0/rpc_stats
4692
4693         local percent=0
4694         local have_ppr=false
4695         $LCTL get_param $proc_osc0/rpc_stats |
4696                 while read PPR RRPC RPCT RCUM BAR WRPC WPCT WCUM; do
4697                         # skip lines until we are at the RPC histogram data
4698                         [ "$PPR" == "pages" ] && have_ppr=true && continue
4699                         $have_ppr || continue
4700
4701                         # we only want the percent stat for < 16 pages
4702                         [[ $(echo $PPR | tr -d ':') -ge $pages ]] && break
4703
4704                         percent=$((percent + WPCT))
4705                         if [[ $percent -gt 15 ]]; then
4706                                 error "less than 16-pages write RPCs" \
4707                                       "$percent% > 15%"
4708                                 break
4709                         fi
4710                 done
4711         rm -rf $TDIR
4712 }
4713 run_test 42e "verify sub-RPC writes are not done synchronously"
4714
4715 test_43A() { # was test_43
4716         test_mkdir $DIR/$tdir
4717         cp -p /bin/ls $DIR/$tdir/$tfile
4718         $MULTIOP $DIR/$tdir/$tfile Ow_c &
4719         pid=$!
4720         # give multiop a chance to open
4721         sleep 1
4722
4723         $DIR/$tdir/$tfile && error "execute $DIR/$tdir/$tfile succeeded" || true
4724         kill -USR1 $pid
4725 }
4726 run_test 43A "execution of file opened for write should return -ETXTBSY"
4727
4728 test_43a() {
4729         test_mkdir $DIR/$tdir
4730         cp -p $(which sleep) $DIR/$tdir/sleep || error "can't copy"
4731         $DIR/$tdir/sleep 60 &
4732         SLEEP_PID=$!
4733         # Make sure exec of $tdir/sleep wins race with truncate
4734         sleep 1
4735         $MULTIOP $DIR/$tdir/sleep Oc && error "expected error, got success"
4736         kill $SLEEP_PID
4737 }
4738 run_test 43a "open(RDWR) of file being executed should return -ETXTBSY"
4739
4740 test_43b() {
4741         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4742
4743         test_mkdir $DIR/$tdir
4744         cp -p $(which sleep) $DIR/$tdir/sleep || error "can't copy"
4745         $DIR/$tdir/sleep 60 &
4746         SLEEP_PID=$!
4747         # Make sure exec of $tdir/sleep wins race with truncate
4748         sleep 1
4749         $TRUNCATE $DIR/$tdir/sleep 0 && error "expected error, got success"
4750         kill $SLEEP_PID
4751 }
4752 run_test 43b "truncate of file being executed should return -ETXTBSY"
4753
4754 test_43c() {
4755         local testdir="$DIR/$tdir"
4756         test_mkdir $testdir
4757         cp $SHELL $testdir/
4758         ( cd $(dirname $SHELL) && md5sum $(basename $SHELL) ) |
4759                 ( cd $testdir && md5sum -c )
4760 }
4761 run_test 43c "md5sum of copy into lustre"
4762
4763 test_44A() { # was test_44
4764         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
4765
4766         dd if=/dev/zero of=$DIR/f1 bs=4k count=1 seek=1023
4767         dd if=$DIR/f1 bs=4k count=1 > /dev/null
4768 }
4769 run_test 44A "zero length read from a sparse stripe"
4770
4771 test_44a() {
4772         local nstripe=$($LCTL lov_getconfig $DIR | grep default_stripe_count: |
4773                 awk '{ print $2 }')
4774         [ -z "$nstripe" ] && skip "can't get stripe info"
4775         [[ $nstripe -gt $OSTCOUNT ]] &&
4776                 skip "Wrong default_stripe_count: $nstripe OSTCOUNT: $OSTCOUNT"
4777
4778         local stride=$($LCTL lov_getconfig $DIR | grep default_stripe_size: |
4779                 awk '{ print $2 }')
4780         if [[ $nstripe -eq 0 || $nstripe -eq -1 ]]; then
4781                 nstripe=$($LCTL lov_getconfig $DIR | grep obd_count: |
4782                         awk '{ print $2 }')
4783         fi
4784
4785         OFFSETS="0 $((stride/2)) $((stride-1))"
4786         for offset in $OFFSETS; do
4787                 for i in $(seq 0 $((nstripe-1))); do
4788                         local GLOBALOFFSETS=""
4789                         # size in Bytes
4790                         local size=$((((i + 2 * $nstripe )*$stride + $offset)))
4791                         local myfn=$DIR/d44a-$size
4792                         echo "--------writing $myfn at $size"
4793                         ll_sparseness_write $myfn $size ||
4794                                 error "ll_sparseness_write"
4795                         GLOBALOFFSETS="$GLOBALOFFSETS $size"
4796                         ll_sparseness_verify $myfn $GLOBALOFFSETS ||
4797                                 error "ll_sparseness_verify $GLOBALOFFSETS"
4798
4799                         for j in $(seq 0 $((nstripe-1))); do
4800                                 # size in Bytes
4801                                 size=$((((j + $nstripe )*$stride + $offset)))
4802                                 ll_sparseness_write $myfn $size ||
4803                                         error "ll_sparseness_write"
4804                                 GLOBALOFFSETS="$GLOBALOFFSETS $size"
4805                         done
4806                         ll_sparseness_verify $myfn $GLOBALOFFSETS ||
4807                                 error "ll_sparseness_verify $GLOBALOFFSETS"
4808                         rm -f $myfn
4809                 done
4810         done
4811 }
4812 run_test 44a "test sparse pwrite ==============================="
4813
4814 dirty_osc_total() {
4815         tot=0
4816         for d in `lctl get_param -n ${OSC}.*.cur_dirty_bytes`; do
4817                 tot=$(($tot + $d))
4818         done
4819         echo $tot
4820 }
4821 do_dirty_record() {
4822         before=`dirty_osc_total`
4823         echo executing "\"$*\""
4824         eval $*
4825         after=`dirty_osc_total`
4826         echo before $before, after $after
4827 }
4828 test_45() {
4829         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4830
4831         f="$DIR/f45"
4832         # Obtain grants from OST if it supports it
4833         echo blah > ${f}_grant
4834         stop_writeback
4835         sync
4836         do_dirty_record "echo blah > $f"
4837         [[ $before -eq $after ]] && error "write wasn't cached"
4838         do_dirty_record "> $f"
4839         [[ $before -gt $after ]] || error "truncate didn't lower dirty count"
4840         do_dirty_record "echo blah > $f"
4841         [[ $before -eq $after ]] && error "write wasn't cached"
4842         do_dirty_record "sync"
4843         [[ $before -gt $after ]] || error "writeback didn't lower dirty count"
4844         do_dirty_record "echo blah > $f"
4845         [[ $before -eq $after ]] && error "write wasn't cached"
4846         do_dirty_record "cancel_lru_locks osc"
4847         [[ $before -gt $after ]] ||
4848                 error "lock cancellation didn't lower dirty count"
4849         start_writeback
4850 }
4851 run_test 45 "osc io page accounting ============================"
4852
4853 # in a 2 stripe file (lov.sh), page 1023 maps to page 511 in its object.  this
4854 # test tickles a bug where re-dirtying a page was failing to be mapped to the
4855 # objects offset and an assert hit when an rpc was built with 1023's mapped
4856 # offset 511 and 511's raw 511 offset. it also found general redirtying bugs.
4857 test_46() {
4858         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4859
4860         f="$DIR/f46"
4861         stop_writeback
4862         sync
4863         dd if=/dev/zero of=$f bs=$PAGE_SIZE seek=511 count=1
4864         sync
4865         dd conv=notrunc if=/dev/zero of=$f bs=$PAGE_SIZE seek=1023 count=1
4866         dd conv=notrunc if=/dev/zero of=$f bs=$PAGE_SIZE seek=511 count=1
4867         sync
4868         start_writeback
4869 }
4870 run_test 46 "dirtying a previously written page ================"
4871
4872 # test_47 is removed "Device nodes check" is moved to test_28
4873
4874 test_48a() { # bug 2399
4875         [ "$mds1_FSTYPE" = "zfs" ] &&
4876         [ $MDS1_VERSION -lt $(version_code 2.3.63) ] &&
4877                 skip "MDS prior to 2.3.63 handle ZFS dir .. incorrectly"
4878
4879         test_mkdir $DIR/$tdir
4880         cd $DIR/$tdir
4881         mv $DIR/$tdir $DIR/$tdir.new || error "move directory failed"
4882         test_mkdir $DIR/$tdir
4883         touch foo || error "'touch foo' failed after recreating cwd"
4884         test_mkdir bar
4885         touch .foo || error "'touch .foo' failed after recreating cwd"
4886         test_mkdir .bar
4887         ls . > /dev/null || error "'ls .' failed after recreating cwd"
4888         ls .. > /dev/null || error "'ls ..' failed after removing cwd"
4889         cd . || error "'cd .' failed after recreating cwd"
4890         mkdir . && error "'mkdir .' worked after recreating cwd"
4891         rmdir . && error "'rmdir .' worked after recreating cwd"
4892         ln -s . baz || error "'ln -s .' failed after recreating cwd"
4893         cd .. || error "'cd ..' failed after recreating cwd"
4894 }
4895 run_test 48a "Access renamed working dir (should return errors)="
4896
4897 test_48b() { # bug 2399
4898         rm -rf $DIR/$tdir
4899         test_mkdir $DIR/$tdir
4900         cd $DIR/$tdir
4901         rmdir $DIR/$tdir || error "remove cwd $DIR/$tdir failed"
4902         touch foo && error "'touch foo' worked after removing cwd"
4903         mkdir foo && error "'mkdir foo' worked after removing cwd"
4904         touch .foo && error "'touch .foo' worked after removing cwd"
4905         mkdir .foo && error "'mkdir .foo' worked after removing cwd"
4906         ls . > /dev/null && error "'ls .' worked after removing cwd"
4907         ls .. > /dev/null || error "'ls ..' failed after removing cwd"
4908         mkdir . && error "'mkdir .' worked after removing cwd"
4909         rmdir . && error "'rmdir .' worked after removing cwd"
4910         ln -s . foo && error "'ln -s .' worked after removing cwd"
4911         cd .. || echo "'cd ..' failed after removing cwd `pwd`"  #bug 3517
4912 }
4913 run_test 48b "Access removed working dir (should return errors)="
4914
4915 test_48c() { # bug 2350
4916         #lctl set_param debug=-1
4917         #set -vx
4918         rm -rf $DIR/$tdir
4919         test_mkdir -p $DIR/$tdir/dir
4920         cd $DIR/$tdir/dir
4921         $TRACE rmdir $DIR/$tdir/dir || error "remove cwd $DIR/$tdir/dir failed"
4922         $TRACE touch foo && error "touch foo worked after removing cwd"
4923         $TRACE mkdir foo && error "'mkdir foo' worked after removing cwd"
4924         touch .foo && error "touch .foo worked after removing cwd"
4925         mkdir .foo && error "mkdir .foo worked after removing cwd"
4926         $TRACE ls . && error "'ls .' worked after removing cwd"
4927         $TRACE ls .. || error "'ls ..' failed after removing cwd"
4928         $TRACE mkdir . && error "'mkdir .' worked after removing cwd"
4929         $TRACE rmdir . && error "'rmdir .' worked after removing cwd"
4930         $TRACE ln -s . foo && error "'ln -s .' worked after removing cwd"
4931         $TRACE cd .. || echo "'cd ..' failed after removing cwd `pwd`" #bug 3415
4932 }
4933 run_test 48c "Access removed working subdir (should return errors)"
4934
4935 test_48d() { # bug 2350
4936         #lctl set_param debug=-1
4937         #set -vx
4938         rm -rf $DIR/$tdir
4939         test_mkdir -p $DIR/$tdir/dir
4940         cd $DIR/$tdir/dir
4941         $TRACE rmdir $DIR/$tdir/dir || error "remove cwd $DIR/$tdir/dir failed"
4942         $TRACE rmdir $DIR/$tdir || error "remove parent $DIR/$tdir failed"
4943         $TRACE touch foo && error "'touch foo' worked after removing parent"
4944         $TRACE mkdir foo && error "mkdir foo worked after removing parent"
4945         touch .foo && error "'touch .foo' worked after removing parent"
4946         mkdir .foo && error "mkdir .foo worked after removing parent"
4947         $TRACE ls . && error "'ls .' worked after removing parent"
4948         $TRACE ls .. && error "'ls ..' worked after removing parent"
4949         $TRACE mkdir . && error "'mkdir .' worked after removing parent"
4950         $TRACE rmdir . && error "'rmdir .' worked after removing parent"
4951         $TRACE ln -s . foo && error "'ln -s .' worked after removing parent"
4952         true
4953 }
4954 run_test 48d "Access removed parent subdir (should return errors)"
4955
4956 test_48e() { # bug 4134
4957         #lctl set_param debug=-1
4958         #set -vx
4959         rm -rf $DIR/$tdir
4960         test_mkdir -p $DIR/$tdir/dir
4961         cd $DIR/$tdir/dir
4962         $TRACE rmdir $DIR/$tdir/dir || error "remove cwd $DIR/$tdir/dir failed"
4963         $TRACE rmdir $DIR/$tdir || error "remove parent $DIR/$tdir failed"
4964         $TRACE touch $DIR/$tdir || error "'touch $DIR/$tdir' failed"
4965         $TRACE chmod +x $DIR/$tdir || error "'chmod +x $DIR/$tdir' failed"
4966         # On a buggy kernel addition of "touch foo" after cd .. will
4967         # produce kernel oops in lookup_hash_it
4968         touch ../foo && error "'cd ..' worked after recreate parent"
4969         cd $DIR
4970         $TRACE rm $DIR/$tdir || error "rm '$DIR/$tdir' failed"
4971 }
4972 run_test 48e "Access to recreated parent subdir (should return errors)"
4973
4974 test_49() { # LU-1030
4975         [ $PARALLEL == "yes" ] && skip "skip parallel run"
4976         remote_ost_nodsh && skip "remote OST with nodsh"
4977
4978         # get ost1 size - lustre-OST0000
4979         ost1_size=$(do_facet ost1 $LFS df | grep ${ost1_svc} |
4980                 awk '{ print $4 }')
4981         # write 800M at maximum
4982         [[ $ost1_size -lt 2 ]] && ost1_size=2
4983         [[ $ost1_size -gt 819200 ]] && ost1_size=819200
4984
4985         $LFS setstripe -c 1 -i 0 $DIR/$tfile
4986         dd if=/dev/zero of=$DIR/$tfile bs=4k count=$((ost1_size >> 2)) &
4987         local dd_pid=$!
4988
4989         # change max_pages_per_rpc while writing the file
4990         local osc1_mppc=osc.$(get_osc_import_name client ost1).max_pages_per_rpc
4991         local orig_mppc=$($LCTL get_param -n $osc1_mppc)
4992         # loop until dd process exits
4993         while ps ax -opid | grep -wq $dd_pid; do
4994                 $LCTL set_param $osc1_mppc=$((RANDOM % 256 + 1))
4995                 sleep $((RANDOM % 5 + 1))
4996         done
4997         # restore original max_pages_per_rpc
4998         $LCTL set_param $osc1_mppc=$orig_mppc
4999         rm $DIR/$tfile || error "rm $DIR/$tfile failed"
5000 }
5001 run_test 49 "Change max_pages_per_rpc won't break osc extent"
5002
5003 test_50() {
5004         # bug 1485
5005         test_mkdir $DIR/$tdir
5006         cd $DIR/$tdir
5007         ls /proc/$$/cwd || error "ls /proc/$$/cwd failed"
5008 }
5009 run_test 50 "special situations: /proc symlinks  ==============="
5010
5011 test_51a() {    # was test_51
5012         # bug 1516 - create an empty entry right after ".." then split dir
5013         test_mkdir -c1 $DIR/$tdir
5014         touch $DIR/$tdir/foo
5015         $MCREATE $DIR/$tdir/bar
5016         rm $DIR/$tdir/foo
5017         createmany -m $DIR/$tdir/longfile 201
5018         FNUM=202
5019         while [[ $(ls -sd $DIR/$tdir | awk '{ print $1 }') -eq 4 ]]; do
5020                 $MCREATE $DIR/$tdir/longfile$FNUM
5021                 FNUM=$(($FNUM + 1))
5022                 echo -n "+"
5023         done
5024         echo
5025         ls -l $DIR/$tdir > /dev/null || error "ls -l $DIR/$tdir failed"
5026 }
5027 run_test 51a "special situations: split htree with empty entry =="
5028
5029 cleanup_print_lfs_df () {
5030         trap 0
5031         $LFS df
5032         $LFS df -i
5033 }
5034
5035 test_51b() {
5036         [ $PARALLEL == "yes" ] && skip "skip parallel run"
5037
5038         local dir=$DIR/$tdir
5039         local nrdirs=$((65536 + 100))
5040
5041         # cleanup the directory
5042         rm -fr $dir
5043
5044         test_mkdir -c1 $dir
5045
5046         $LFS df
5047         $LFS df -i
5048         local mdtidx=$(printf "%04x" $($LFS getstripe -m $dir))
5049         local numfree=$(lctl get_param -n mdc.$FSNAME-MDT$mdtidx*.filesfree)
5050         [[ $numfree -lt $nrdirs ]] &&
5051                 skip "not enough free inodes ($numfree) on MDT$mdtidx"
5052
5053         # need to check free space for the directories as well
5054         local blkfree=$(lctl get_param -n mdc.$FSNAME-MDT$mdtidx*.kbytesavail)
5055         numfree=$(( blkfree / $(fs_inode_ksize) ))
5056         [[ $numfree -lt $nrdirs ]] && skip "not enough blocks ($numfree)"
5057
5058         trap cleanup_print_lfs_df EXIT
5059
5060         # create files
5061         createmany -d $dir/d $nrdirs || {
5062                 unlinkmany $dir/d $nrdirs
5063                 error "failed to create $nrdirs subdirs in MDT$mdtidx:$dir"
5064         }
5065
5066         # really created :
5067         nrdirs=$(ls -U $dir | wc -l)
5068
5069         # unlink all but 100 subdirectories, then check it still works
5070         local left=100
5071         local delete=$((nrdirs - left))
5072
5073         $LFS df
5074         $LFS df -i
5075
5076         # for ldiskfs the nlink count should be 1, but this is OSD specific
5077         # and so this is listed for informational purposes only
5078         echo "nlink before: $(stat -c %h $dir), created before: $nrdirs"
5079         unlinkmany -d $dir/d $delete ||
5080                 error "unlink of first $delete subdirs failed"
5081
5082         echo "nlink between: $(stat -c %h $dir)"
5083         local found=$(ls -U $dir | wc -l)
5084         [ $found -ne $left ] &&
5085                 error "can't find subdirs: found only $found, expected $left"
5086
5087         unlinkmany -d $dir/d $delete $left ||
5088                 error "unlink of second $left subdirs failed"
5089         # regardless of whether the backing filesystem tracks nlink accurately
5090         # or not, the nlink count shouldn't be more than "." and ".." here
5091         local after=$(stat -c %h $dir)
5092         [[ $after -gt 2 ]] && error "nlink after: $after > 2" ||
5093                 echo "nlink after: $after"
5094
5095         cleanup_print_lfs_df
5096 }
5097 run_test 51b "exceed 64k subdirectory nlink limit on create, verify unlink"
5098
5099 test_51d() {
5100         [ $PARALLEL == "yes" ] && skip "skip parallel run"
5101         [[ $OSTCOUNT -lt 3 ]] && skip_env "needs >= 3 OSTs"
5102
5103         test_mkdir $DIR/$tdir
5104         createmany -o $DIR/$tdir/t- 1000
5105         $LFS getstripe $DIR/$tdir > $TMP/$tfile
5106         for N in $(seq 0 $((OSTCOUNT - 1))); do
5107                 OBJS[$N]=$(awk -vobjs=0 '($1 == '$N') { objs += 1 } \
5108                         END { printf("%0.0f", objs) }' $TMP/$tfile)
5109                 OBJS0[$N]=$(grep -A 1 idx $TMP/$tfile | awk -vobjs=0 \
5110                         '($1 == '$N') { objs += 1 } \
5111                         END { printf("%0.0f", objs) }')
5112                 log "OST$N has ${OBJS[$N]} objects, ${OBJS0[$N]} are index 0"
5113         done
5114         unlinkmany $DIR/$tdir/t- 1000
5115
5116         NLAST=0
5117         for N in $(seq 1 $((OSTCOUNT - 1))); do
5118                 [[ ${OBJS[$N]} -lt $((${OBJS[$NLAST]} - 20)) ]] &&
5119                         error "OST $N has less objects vs OST $NLAST" \
5120                               " (${OBJS[$N]} < ${OBJS[$NLAST]}"
5121                 [[ ${OBJS[$N]} -gt $((${OBJS[$NLAST]} + 20)) ]] &&
5122                         error "OST $N has less objects vs OST $NLAST" \
5123                               " (${OBJS[$N]} < ${OBJS[$NLAST]}"
5124
5125                 [[ ${OBJS0[$N]} -lt $((${OBJS0[$NLAST]} - 20)) ]] &&
5126                         error "OST $N has less #0 objects vs OST $NLAST" \
5127                               " (${OBJS0[$N]} < ${OBJS0[$NLAST]}"
5128                 [[ ${OBJS0[$N]} -gt $((${OBJS0[$NLAST]} + 20)) ]] &&
5129                         error "OST $N has less #0 objects vs OST $NLAST" \
5130                               " (${OBJS0[$N]} < ${OBJS0[$NLAST]}"
5131                 NLAST=$N
5132         done
5133         rm -f $TMP/$tfile
5134 }
5135 run_test 51d "check object distribution"
5136
5137 test_51e() {
5138         if [ "$mds1_FSTYPE" != ldiskfs ]; then
5139                 skip_env "ldiskfs only test"
5140         fi
5141
5142         test_mkdir -c1 $DIR/$tdir
5143         test_mkdir -c1 $DIR/$tdir/d0
5144
5145         touch $DIR/$tdir/d0/foo
5146         createmany -l $DIR/$tdir/d0/foo $DIR/$tdir/d0/f- 65001 &&
5147                 error "file exceed 65000 nlink limit!"
5148         unlinkmany $DIR/$tdir/d0/f- 65001
5149         return 0
5150 }
5151 run_test 51e "check file nlink limit"
5152
5153 test_51f() {
5154         test_mkdir $DIR/$tdir
5155
5156         local max=100000
5157         local ulimit_old=$(ulimit -n)
5158         local spare=20 # number of spare fd's for scripts/libraries, etc.
5159         local mdt=$($LFS getstripe -m $DIR/$tdir)
5160         local numfree=$($LFS df -i $DIR/$tdir | awk '/MDT:'$mdt'/ { print $4 }')
5161
5162         echo "MDT$mdt numfree=$numfree, max=$max"
5163         [[ $numfree -gt $max ]] && numfree=$max || numfree=$((numfree * 7 / 8))
5164         if [ $((numfree + spare)) -gt $ulimit_old ]; then
5165                 while ! ulimit -n $((numfree + spare)); do
5166                         numfree=$((numfree * 3 / 4))
5167                 done
5168                 echo "changed ulimit from $ulimit_old to $((numfree + spare))"
5169         else
5170                 echo "left ulimit at $ulimit_old"
5171         fi
5172
5173         createmany -o -k -t 120 $DIR/$tdir/f $numfree || {
5174                 unlinkmany $DIR/$tdir/f $numfree
5175                 error "create+open $numfree files in $DIR/$tdir failed"
5176         }
5177         ulimit -n $ulimit_old
5178
5179         # if createmany exits at 120s there will be fewer than $numfree files
5180         unlinkmany $DIR/$tdir/f $numfree || true
5181 }
5182 run_test 51f "check many open files limit"
5183
5184 test_52a() {
5185         [ -f $DIR/$tdir/foo ] && chattr -a $DIR/$tdir/foo
5186         test_mkdir $DIR/$tdir
5187         touch $DIR/$tdir/foo
5188         chattr +a $DIR/$tdir/foo || error "chattr +a failed"
5189         echo bar >> $DIR/$tdir/foo || error "append bar failed"
5190         cp /etc/hosts $DIR/$tdir/foo && error "cp worked"
5191         rm -f $DIR/$tdir/foo 2>/dev/null && error "rm worked"
5192         link $DIR/$tdir/foo $DIR/$tdir/foo_link 2>/dev/null &&
5193                                         error "link worked"
5194         echo foo >> $DIR/$tdir/foo || error "append foo failed"
5195         mrename $DIR/$tdir/foo $DIR/$tdir/foo_ren && error "rename worked"
5196         lsattr $DIR/$tdir/foo | egrep -q "^-+a[-e]+ $DIR/$tdir/foo" ||
5197                                                      error "lsattr"
5198         chattr -a $DIR/$tdir/foo || error "chattr -a failed"
5199         cp -r $DIR/$tdir $TMP/
5200         rm -fr $DIR/$tdir $TMP/$tdir || error "cleanup rm failed"
5201 }
5202 run_test 52a "append-only flag test (should return errors)"
5203
5204 test_52b() {
5205         [ -f $DIR/$tdir/foo ] && chattr -i $DIR/$tdir/foo
5206         test_mkdir $DIR/$tdir
5207         touch $DIR/$tdir/foo
5208         chattr +i $DIR/$tdir/foo || error "chattr +i failed"
5209         cat test > $DIR/$tdir/foo && error "cat test worked"
5210         cp /etc/hosts $DIR/$tdir/foo && error "cp worked"
5211         rm -f $DIR/$tdir/foo 2>/dev/null && error "rm worked"
5212         link $DIR/$tdir/foo $DIR/$tdir/foo_link 2>/dev/null &&
5213                                         error "link worked"
5214         echo foo >> $DIR/$tdir/foo && error "echo worked"
5215         mrename $DIR/$tdir/foo $DIR/$tdir/foo_ren && error "rename worked"
5216         [ -f $DIR/$tdir/foo ] || error "$tdir/foo is not a file"
5217         [ -f $DIR/$tdir/foo_ren ] && error "$tdir/foo_ren is not a file"
5218         lsattr $DIR/$tdir/foo | egrep -q "^-+i[-e]+ $DIR/$tdir/foo" ||
5219                                                         error "lsattr"
5220         chattr -i $DIR/$tdir/foo || error "chattr failed"
5221
5222         rm -fr $DIR/$tdir || error "unable to remove $DIR/$tdir"
5223 }
5224 run_test 52b "immutable flag test (should return errors) ======="
5225
5226 test_53() {
5227         [ $PARALLEL == "yes" ] && skip "skip parallel run"
5228         remote_mds_nodsh && skip "remote MDS with nodsh"
5229         remote_ost_nodsh && skip "remote OST with nodsh"
5230
5231         local param
5232         local param_seq
5233         local ostname
5234         local mds_last
5235         local mds_last_seq
5236         local ost_last
5237         local ost_last_seq
5238         local ost_last_id
5239         local ostnum
5240         local node
5241         local found=false
5242         local support_last_seq=true
5243
5244         [[ $MDS1_VERSION -ge $(version_code 2.3.60) ]] ||
5245                 support_last_seq=false
5246
5247         # only test MDT0000
5248         local mdtosc=$(get_mdtosc_proc_path $SINGLEMDS)
5249         local value
5250         for value in $(do_facet $SINGLEMDS \
5251                        $LCTL get_param osp.$mdtosc.prealloc_last_id) ; do
5252                 param=$(echo ${value[0]} | cut -d "=" -f1)
5253                 ostname=$(echo $param | cut -d "." -f2 | cut -d - -f 1-2)
5254
5255                 if $support_last_seq; then
5256                         param_seq=$(echo $param |
5257                                 sed -e s/prealloc_last_id/prealloc_last_seq/g)
5258                         mds_last_seq=$(do_facet $SINGLEMDS \
5259                                        $LCTL get_param -n $param_seq)
5260                 fi
5261                 mds_last=$(do_facet $SINGLEMDS $LCTL get_param -n $param)
5262
5263                 ostnum=$(index_from_ostuuid ${ostname}_UUID)
5264                 node=$(facet_active_host ost$((ostnum+1)))
5265                 param="obdfilter.$ostname.last_id"
5266                 for ost_last in $(do_node $node $LCTL get_param -n $param) ; do
5267                         echo "$ostname.last_id=$ost_last; MDS.last_id=$mds_last"
5268                         ost_last_id=$ost_last
5269
5270                         if $support_last_seq; then
5271                                 ost_last_id=$(echo $ost_last |
5272                                               awk -F':' '{print $2}' |
5273                                               sed -e "s/^0x//g")
5274                                 ost_last_seq=$(echo $ost_last |
5275                                                awk -F':' '{print $1}')
5276                                 [[ $ost_last_seq = $mds_last_seq ]] || continue
5277                         fi
5278
5279                         if [[ $ost_last_id != $mds_last ]]; then
5280                                 error "$ost_last_id != $mds_last"
5281                         else
5282                                 found=true
5283                                 break
5284                         fi
5285                 done
5286         done
5287         $found || error "can not match last_seq/last_id for $mdtosc"
5288         return 0
5289 }
5290 run_test 53 "verify that MDS and OSTs agree on pre-creation ===="
5291
5292 test_54a() {
5293         perl -MSocket -e ';' || skip "no Socket perl module installed"
5294
5295         $SOCKETSERVER $DIR/socket ||
5296                 error "$SOCKETSERVER $DIR/socket failed: $?"
5297         $SOCKETCLIENT $DIR/socket ||
5298                 error "$SOCKETCLIENT $DIR/socket failed: $?"
5299         $MUNLINK $DIR/socket || error "$MUNLINK $DIR/socket failed: $?"
5300 }
5301 run_test 54a "unix domain socket test =========================="
5302
5303 test_54b() {
5304         f="$DIR/f54b"
5305         mknod $f c 1 3
5306         chmod 0666 $f
5307         dd if=/dev/zero of=$f bs=$PAGE_SIZE count=1
5308 }
5309 run_test 54b "char device works in lustre ======================"
5310
5311 find_loop_dev() {
5312         [ -b /dev/loop/0 ] && LOOPBASE=/dev/loop/
5313         [ -b /dev/loop0 ] && LOOPBASE=/dev/loop
5314         [ -z "$LOOPBASE" ] && echo "/dev/loop/0 and /dev/loop0 gone?" && return
5315
5316         for i in $(seq 3 7); do
5317                 losetup $LOOPBASE$i > /dev/null 2>&1 && continue
5318                 LOOPDEV=$LOOPBASE$i
5319                 LOOPNUM=$i
5320                 break
5321         done
5322 }
5323
5324 cleanup_54c() {
5325         local rc=0
5326         loopdev="$DIR/loop54c"
5327
5328         trap 0
5329         $UMOUNT $DIR/$tdir || rc=$?
5330         losetup -d $loopdev || true
5331         losetup -d $LOOPDEV || true
5332         rm -rf $loopdev $DIR/$tfile $DIR/$tdir
5333         return $rc
5334 }
5335
5336 test_54c() {
5337         [ $PARALLEL == "yes" ] && skip "skip parallel run"
5338
5339         loopdev="$DIR/loop54c"
5340
5341         find_loop_dev
5342         [ -z "$LOOPNUM" ] && skip_env "couldn't find empty loop device"
5343         trap cleanup_54c EXIT
5344         mknod $loopdev b 7 $LOOPNUM
5345         echo "make a loop file system with $DIR/$tfile on $loopdev ($LOOPNUM)."
5346         dd if=/dev/zero of=$DIR/$tfile bs=$PAGE_SIZE seek=1024 count=1 > /dev/null
5347         losetup $loopdev $DIR/$tfile ||
5348                 error "can't set up $loopdev for $DIR/$tfile"
5349         mkfs.ext2 $loopdev || error "mke2fs on $loopdev"
5350         test_mkdir $DIR/$tdir
5351         mount -t ext2 $loopdev $DIR/$tdir ||
5352                 error "error mounting $loopdev on $DIR/$tdir"
5353         dd if=/dev/zero of=$DIR/$tdir/tmp bs=$PAGE_SIZE count=30 ||
5354                 error "dd write"
5355         df $DIR/$tdir
5356         dd if=$DIR/$tdir/tmp of=/dev/zero bs=$PAGE_SIZE count=30 ||
5357                 error "dd read"
5358         cleanup_54c
5359 }
5360 run_test 54c "block device works in lustre ====================="
5361
5362 test_54d() {
5363         f="$DIR/f54d"
5364         string="aaaaaa"
5365         mknod $f p
5366         [ "$string" = $(echo $string > $f | cat $f) ] || error "$f != $string"
5367 }
5368 run_test 54d "fifo device works in lustre ======================"
5369
5370 test_54e() {
5371         f="$DIR/f54e"
5372         string="aaaaaa"
5373         cp -aL /dev/console $f
5374         echo $string > $f || error "echo $string to $f failed"
5375 }
5376 run_test 54e "console/tty device works in lustre ======================"
5377
5378 test_56a() {
5379         local numfiles=3
5380         local dir=$DIR/$tdir
5381
5382         rm -rf $dir
5383         test_mkdir -p $dir/dir
5384         for i in $(seq $numfiles); do
5385                 touch $dir/file$i
5386                 touch $dir/dir/file$i
5387         done
5388
5389         local numcomp=$($LFS getstripe --component-count $dir)
5390
5391         [[ $numcomp == 0 ]] && numcomp=1
5392
5393         # test lfs getstripe with --recursive
5394         local filenum=$($LFS getstripe -r $dir | egrep -c "obdidx|l_ost_idx")
5395
5396         [[ $filenum -eq $((numfiles * 2)) ]] ||
5397                 error "$LFS getstripe -r: found $filenum != $((numfiles * 2))"
5398         filenum=$($LFS getstripe $dir | egrep -c "obdidx|l_ost_idx")
5399         [[ $filenum -eq $numfiles ]] ||
5400                 error "$LFS getstripe $dir: found $filenum, not $numfiles"
5401         echo "$LFS getstripe showed obdidx or l_ost_idx"
5402
5403         # test lfs getstripe with file instead of dir
5404         filenum=$($LFS getstripe $dir/file1 | egrep -c "obdidx|l_ost_idx")
5405         [[ $filenum -eq 1 ]] ||
5406                 error "$LFS getstripe $dir/file1: found $filenum, not 1"
5407         echo "$LFS getstripe file1 passed"
5408
5409         #test lfs getstripe with --verbose
5410         filenum=$($LFS getstripe --verbose $dir | grep -c lmm_magic)
5411         [[ $filenum -eq $((numfiles * numcomp)) ]] ||
5412                 error "$LFS getstripe --verbose $dir: "\
5413                       "got $filenum want $((numfiles * numcomp)) lmm_magic"
5414         [[ $($LFS getstripe $dir | grep -c lmm_magic) -eq 0 ]] ||
5415                 error "$LFS getstripe $dir: showed lmm_magic"
5416
5417         #test lfs getstripe with -v prints lmm_fid
5418         filenum=$($LFS getstripe -v $dir | grep -c lmm_fid)
5419         [[ $filenum -eq $((numfiles * numcomp)) ]] ||
5420                 error "$LFS getstripe -v $dir: "\
5421                       "got $filenum want $((numfiles * numcomp)) lmm_fid"
5422         [[ $($LFS getstripe $dir | grep -c lmm_fid) -eq 0 ]] ||
5423                 error "$LFS getstripe $dir: showed lmm_fid by default"
5424         echo "$LFS getstripe --verbose passed"
5425
5426         #check for FID information
5427         local fid1=$($LFS getstripe --fid $dir/file1)
5428         local fid2=$($LFS getstripe --verbose $dir/file1 |
5429                      awk '/lmm_fid: / { print $2; exit; }')
5430         local fid3=$($LFS path2fid $dir/file1)
5431
5432         [ "$fid1" != "$fid2" ] &&
5433                 error "getstripe --fid '$fid1' != getstripe --verbose '$fid2'"
5434         [ "$fid1" != "$fid3" ] &&
5435                 error "getstripe --fid '$fid1' != lfs path2fid '$fid3'"
5436         echo "$LFS getstripe --fid passed"
5437
5438         #test lfs getstripe with --obd
5439         $LFS getstripe --obd wrong_uuid $dir 2>&1 | grep -q "unknown obduuid" ||
5440                 error "$LFS getstripe --obd wrong_uuid: should return error"
5441
5442         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
5443
5444         local ostidx=1
5445         local obduuid=$(ostuuid_from_index $ostidx)
5446         local found=$($LFS getstripe -r --obd $obduuid $dir |
5447                 grep 'lmm_stripe_offset:' | grep -c " $ostidx\$")
5448
5449         filenum=$($LFS getstripe -ir $dir | grep -c "^$ostidx\$")
5450         [[ $($LFS getstripe -id $dir) -ne $ostidx ]] ||
5451                 ((filenum--))
5452         [[ $($LFS getstripe -id $dir/dir) -ne $ostidx ]] ||
5453                 ((filenum--))
5454
5455         [[ $found -eq $filenum ]] ||
5456                 error "$LFS getstripe --obd: found $found expect $filenum"
5457         [[ $($LFS getstripe -r -v --obd $obduuid $dir |
5458                 sed '/^[         ]*'${ostidx}'[  ]/d' |
5459                 sed -n '/^[      ]*[0-9][0-9]*[  ]/p' | wc -l) -eq 0 ]] ||
5460                 error "$LFS getstripe --obd: should not show file on other obd"
5461         echo "$LFS getstripe --obd passed"
5462 }
5463 run_test 56a "check $LFS getstripe"
5464
5465 test_56b() {
5466         local dir=$DIR/$tdir
5467         local numdirs=3
5468
5469         test_mkdir $dir
5470         for i in $(seq $numdirs); do
5471                 test_mkdir $dir/dir$i
5472         done
5473
5474         # test lfs getdirstripe default mode is non-recursion, which is
5475         # different from lfs getstripe
5476         local dircnt=$($LFS getdirstripe $dir | grep -c lmv_stripe_count)
5477
5478         [[ $dircnt -eq 1 ]] ||
5479                 error "$LFS getdirstripe: found $dircnt, not 1"
5480         dircnt=$($LFS getdirstripe --recursive $dir |
5481                 grep -c lmv_stripe_count)
5482         [[ $dircnt -eq $((numdirs + 1)) ]] ||
5483                 error "$LFS getdirstripe -r: $dircnt, != $((numdirs + 1))"
5484 }
5485 run_test 56b "check $LFS getdirstripe"
5486
5487 test_56c() {
5488         remote_ost_nodsh && skip "remote OST with nodsh"
5489
5490         local ost_idx=0
5491         local ost_name=$(ostname_from_index $ost_idx)
5492         local old_status=$(ost_dev_status $ost_idx)
5493
5494         [[ -z "$old_status" ]] ||
5495                 skip_env "OST $ost_name is in $old_status status"
5496
5497         do_facet ost1 $LCTL set_param -n obdfilter.$ost_name.degraded=1
5498         [[ $OST1_VERSION -ge $(version_code 2.12.55) ]] && do_facet ost1 \
5499                 $LCTL set_param -n obdfilter.$ost_name.no_precreate=1
5500         sleep_maxage
5501
5502         local new_status=$(ost_dev_status $ost_idx)
5503
5504         [[ "$new_status" =~ "D" ]] ||
5505                 error "$ost_name status is '$new_status', missing 'D'"
5506         if [[ $OST1_VERSION -ge $(version_code 2.12.55) ]]; then
5507                 [[ "$new_status" =~ "N" ]] ||
5508                         error "$ost_name status is '$new_status', missing 'N'"
5509         fi
5510
5511         do_facet ost1 $LCTL set_param -n obdfilter.$ost_name.degraded=0
5512         [[ $OST1_VERSION -ge $(version_code 2.12.55) ]] && do_facet ost1 \
5513                 $LCTL set_param -n obdfilter.$ost_name.no_precreate=0
5514         sleep_maxage
5515
5516         new_status=$(ost_dev_status $ost_idx)
5517         [[ ! "$new_status" =~ "D" && ! "$new_status" =~ "N" ]] ||
5518                 error "$ost_name status is '$new_status', has 'D' and/or 'N'"
5519 }
5520 run_test 56c "check 'lfs df' showing device status"
5521
5522 NUMFILES=3
5523 NUMDIRS=3
5524 setup_56() {
5525         local local_tdir="$1"
5526         local local_numfiles="$2"
5527         local local_numdirs="$3"
5528         local dir_params="$4"
5529         local dir_stripe_params="$5"
5530
5531         if [ ! -d "$local_tdir" ] ; then
5532                 test_mkdir -p $dir_stripe_params $local_tdir
5533                 [ "$dir_params" ] && $LFS setstripe $dir_params $local_tdir
5534                 for i in $(seq $local_numfiles) ; do
5535                         touch $local_tdir/file$i
5536                 done
5537                 for i in $(seq $local_numdirs) ; do
5538                         test_mkdir $dir_stripe_params $local_tdir/dir$i
5539                         for j in $(seq $local_numfiles) ; do
5540                                 touch $local_tdir/dir$i/file$j
5541                         done
5542                 done
5543         fi
5544 }
5545
5546 setup_56_special() {
5547         local local_tdir=$1
5548         local local_numfiles=$2
5549         local local_numdirs=$3
5550
5551         setup_56 $local_tdir $local_numfiles $local_numdirs
5552
5553         if [ ! -e "$local_tdir/loop${local_numfiles}b" ] ; then
5554                 for i in $(seq $local_numfiles) ; do
5555                         mknod $local_tdir/loop${i}b b 7 $i
5556                         mknod $local_tdir/null${i}c c 1 3
5557                         ln -s $local_tdir/file1 $local_tdir/link${i}
5558                 done
5559                 for i in $(seq $local_numdirs) ; do
5560                         mknod $local_tdir/dir$i/loop${i}b b 7 $i
5561                         mknod $local_tdir/dir$i/null${i}c c 1 3
5562                         ln -s $local_tdir/dir$i/file1 $local_tdir/dir$i/link${i}
5563                 done
5564         fi
5565 }
5566
5567 test_56g() {
5568         local dir=$DIR/d$(basetest $testnum)g.$TESTSUITE
5569         local expected=$(($NUMDIRS + 2))
5570
5571         setup_56 $dir $NUMFILES $NUMDIRS
5572
5573         # test lfs find with -name
5574         for i in $(seq $NUMFILES) ; do
5575                 local nums=$($LFS find -name "*$i" $dir | wc -l)
5576
5577                 [ $nums -eq $expected ] ||
5578                         error "lfs find -name '*$i' $dir wrong: "\
5579                               "found $nums, expected $expected"
5580         done
5581 }
5582 run_test 56g "check lfs find -name"
5583
5584 test_56h() {
5585         local dir=$DIR/d$(basetest $testnum)g.$TESTSUITE
5586         local expected=$(((NUMDIRS + 1) * (NUMFILES - 1) + NUMFILES))
5587
5588         setup_56 $dir $NUMFILES $NUMDIRS
5589
5590         # test lfs find with ! -name
5591         for i in $(seq $NUMFILES) ; do
5592                 local nums=$($LFS find ! -name "*$i" $dir | wc -l)
5593
5594                 [ $nums -eq $expected ] ||
5595                         error "lfs find ! -name '*$i' $dir wrong: "\
5596                               "found $nums, expected $expected"
5597         done
5598 }
5599 run_test 56h "check lfs find ! -name"
5600
5601 test_56i() {
5602         local dir=$DIR/$tdir
5603
5604         test_mkdir $dir
5605
5606         local cmd="$LFS find -ost $(ostuuid_from_index 0 $dir) $dir"
5607         local out=$($cmd)
5608
5609         [ -z "$out" ] || error "'$cmd' returned directory '$out'"
5610 }
5611 run_test 56i "check 'lfs find -ost UUID' skips directories"
5612
5613 test_56j() {
5614         local dir=$DIR/d$(basetest $testnum)g.$TESTSUITE
5615
5616         setup_56_special $dir $NUMFILES $NUMDIRS
5617
5618         local expected=$((NUMDIRS + 1))
5619         local cmd="$LFS find -type d $dir"
5620         local nums=$($cmd | wc -l)
5621
5622         [ $nums -eq $expected ] ||
5623                 error "'$cmd' wrong: found $nums, expected $expected"
5624 }
5625 run_test 56j "check lfs find -type d"
5626
5627 test_56k() {
5628         local dir=$DIR/d$(basetest $testnum)g.$TESTSUITE
5629
5630         setup_56_special $dir $NUMFILES $NUMDIRS
5631
5632         local expected=$(((NUMDIRS + 1) * NUMFILES))
5633         local cmd="$LFS find -type f $dir"
5634         local nums=$($cmd | wc -l)
5635
5636         [ $nums -eq $expected ] ||
5637                 error "'$cmd' wrong: found $nums, expected $expected"
5638 }
5639 run_test 56k "check lfs find -type f"
5640
5641 test_56l() {
5642         local dir=$DIR/d$(basetest $testnum)g.$TESTSUITE
5643
5644         setup_56_special $dir $NUMFILES $NUMDIRS
5645
5646         local expected=$((NUMDIRS + NUMFILES))
5647         local cmd="$LFS find -type b $dir"
5648         local nums=$($cmd | wc -l)
5649
5650         [ $nums -eq $expected ] ||
5651                 error "'$cmd' wrong: found $nums, expected $expected"
5652 }
5653 run_test 56l "check lfs find -type b"
5654
5655 test_56m() {
5656         local dir=$DIR/d$(basetest $testnum)g.$TESTSUITE
5657
5658         setup_56_special $dir $NUMFILES $NUMDIRS
5659
5660         local expected=$((NUMDIRS + NUMFILES))
5661         local cmd="$LFS find -type c $dir"
5662         local nums=$($cmd | wc -l)
5663         [ $nums -eq $expected ] ||
5664                 error "'$cmd' wrong: found $nums, expected $expected"
5665 }
5666 run_test 56m "check lfs find -type c"
5667
5668 test_56n() {
5669         local dir=$DIR/d$(basetest $testnum)g.$TESTSUITE
5670         setup_56_special $dir $NUMFILES $NUMDIRS
5671
5672         local expected=$((NUMDIRS + NUMFILES))
5673         local cmd="$LFS find -type l $dir"
5674         local nums=$($cmd | wc -l)
5675
5676         [ $nums -eq $expected ] ||
5677                 error "'$cmd' wrong: found $nums, expected $expected"
5678 }
5679 run_test 56n "check lfs find -type l"
5680
5681 test_56o() {
5682         local dir=$DIR/$tdir
5683
5684         setup_56 $dir $NUMFILES $NUMDIRS
5685         utime $dir/file1 > /dev/null || error "utime (1)"
5686         utime $dir/file2 > /dev/null || error "utime (2)"
5687         utime $dir/dir1 > /dev/null || error "utime (3)"
5688         utime $dir/dir2 > /dev/null || error "utime (4)"
5689         utime $dir/dir1/file1 > /dev/null || error "utime (5)"
5690         dd if=/dev/zero count=1 >> $dir/dir1/file1 && sync
5691
5692         local expected=4
5693         local nums=$($LFS find -mtime +0 $dir | wc -l)
5694
5695         [ $nums -eq $expected ] ||
5696                 error "lfs find -mtime +0 $dir: found $nums expect $expected"
5697
5698         expected=12
5699         cmd="$LFS find -mtime 0 $dir"
5700         nums=$($cmd | wc -l)
5701         [ $nums -eq $expected ] ||
5702                 error "'$cmd' wrong: found $nums, expected $expected"
5703 }
5704 run_test 56o "check lfs find -mtime for old files"
5705
5706 test_56ob() {
5707         local dir=$DIR/$tdir
5708         local expected=1
5709         local count=0
5710
5711         # just to make sure there is something that won't be found
5712         test_mkdir $dir
5713         touch $dir/$tfile.now
5714
5715         for age in year week day hour min; do
5716                 count=$((count + 1))
5717
5718                 touch $dir/$tfile-a.$age $dir/$tfile-m.$age
5719                 touch --date="$count $age ago" -a $dir/$tfile-a.$age
5720                 touch --date="$count $age ago" -m $dir/$tfile-m.$age
5721
5722                 local cmd="$LFS find $dir -mtime $count${age:0:1}"
5723                 local nums=$($cmd | wc -l)
5724                 [ $nums -eq $expected ] ||
5725                         error "'$cmd' wrong: found $nums, expected $expected"
5726
5727                 cmd="$LFS find $dir -atime $count${age:0:1}"
5728                 nums=$($cmd | wc -l)
5729                 [ $nums -eq $expected ] ||
5730                         error "'$cmd' wrong: found $nums, expected $expected"
5731         done
5732
5733         sleep 2
5734         cmd="$LFS find $dir -ctime +1s -type f"
5735         nums=$($cmd | wc -l)
5736         (( $nums == $count * 2 + 1)) ||
5737                 error "'$cmd' wrong: found $nums, expected $((expected*2+1))"
5738 }
5739 run_test 56ob "check lfs find -atime -mtime -ctime with units"
5740
5741 test_56p() {
5742         [ $RUNAS_ID -eq $UID ] &&
5743                 skip_env "RUNAS_ID = UID = $UID -- skipping"
5744
5745         local dir=$DIR/$tdir
5746
5747         setup_56 $dir $NUMFILES $NUMDIRS
5748         chown $RUNAS_ID $dir/file* || error "chown $DIR/${tdir}g/file$i failed"
5749
5750         local expected=$NUMFILES
5751         local cmd="$LFS find -uid $RUNAS_ID $dir"
5752         local nums=$($cmd | wc -l)
5753
5754         [ $nums -eq $expected ] ||
5755                 error "'$cmd' wrong: found $nums, expected $expected"
5756
5757         expected=$(((NUMFILES + 1) * NUMDIRS + 1))
5758         cmd="$LFS find ! -uid $RUNAS_ID $dir"
5759         nums=$($cmd | wc -l)
5760         [ $nums -eq $expected ] ||
5761                 error "'$cmd' wrong: found $nums, expected $expected"
5762 }
5763 run_test 56p "check lfs find -uid and ! -uid"
5764
5765 test_56q() {
5766         [ $RUNAS_ID -eq $UID ] &&
5767                 skip_env "RUNAS_ID = UID = $UID -- skipping"
5768
5769         local dir=$DIR/$tdir
5770
5771         setup_56 $dir $NUMFILES $NUMDIRS
5772         chgrp $RUNAS_GID $dir/file* || error "chown $dir/file$i failed"
5773
5774         local expected=$NUMFILES
5775         local cmd="$LFS find -gid $RUNAS_GID $dir"
5776         local nums=$($cmd | wc -l)
5777
5778         [ $nums -eq $expected ] ||
5779                 error "'$cmd' wrong: found $nums, expected $expected"
5780
5781         expected=$(( ($NUMFILES+1) * $NUMDIRS + 1))
5782         cmd="$LFS find ! -gid $RUNAS_GID $dir"
5783         nums=$($cmd | wc -l)
5784         [ $nums -eq $expected ] ||
5785                 error "'$cmd' wrong: found $nums, expected $expected"
5786 }
5787 run_test 56q "check lfs find -gid and ! -gid"
5788
5789 test_56r() {
5790         local dir=$DIR/$tdir
5791
5792         setup_56 $dir $NUMFILES $NUMDIRS
5793
5794         local expected=12
5795         local cmd="$LFS find -size 0 -type f -lazy $dir"
5796         local nums=$($cmd | wc -l)
5797
5798         [ $nums -eq $expected ] ||
5799                 error "'$cmd' wrong: found $nums, expected $expected"
5800         cmd="$LFS find -size 0 -type f $dir"
5801         nums=$($cmd | wc -l)
5802         [ $nums -eq $expected ] ||
5803                 error "'$cmd' wrong: found $nums, expected $expected"
5804
5805         expected=0
5806         cmd="$LFS find ! -size 0 -type f -lazy $dir"
5807         nums=$($cmd | wc -l)
5808         [ $nums -eq $expected ] ||
5809                 error "'$cmd' wrong: found $nums, expected $expected"
5810         cmd="$LFS find ! -size 0 -type f $dir"
5811         nums=$($cmd | wc -l)
5812         [ $nums -eq $expected ] ||
5813                 error "'$cmd' wrong: found $nums, expected $expected"
5814
5815         echo "test" > $dir/$tfile
5816         echo "test2" > $dir/$tfile.2 && sync
5817         expected=1
5818         cmd="$LFS find -size 5 -type f -lazy $dir"
5819         nums=$($cmd | wc -l)
5820         [ $nums -eq $expected ] ||
5821                 error "'$cmd' wrong: found $nums, expected $expected"
5822         cmd="$LFS find -size 5 -type f $dir"
5823         nums=$($cmd | wc -l)
5824         [ $nums -eq $expected ] ||
5825                 error "'$cmd' wrong: found $nums, expected $expected"
5826
5827         expected=1
5828         cmd="$LFS find -size +5 -type f -lazy $dir"
5829         nums=$($cmd | wc -l)
5830         [ $nums -eq $expected ] ||
5831                 error "'$cmd' wrong: found $nums, expected $expected"
5832         cmd="$LFS find -size +5 -type f $dir"
5833         nums=$($cmd | wc -l)
5834         [ $nums -eq $expected ] ||
5835                 error "'$cmd' wrong: found $nums, expected $expected"
5836
5837         expected=2
5838         cmd="$LFS find -size +0 -type f -lazy $dir"
5839         nums=$($cmd | wc -l)
5840         [ $nums -eq $expected ] ||
5841                 error "'$cmd' wrong: found $nums, expected $expected"
5842         cmd="$LFS find -size +0 -type f $dir"
5843         nums=$($cmd | wc -l)
5844         [ $nums -eq $expected ] ||
5845                 error "'$cmd' wrong: found $nums, expected $expected"
5846
5847         expected=2
5848         cmd="$LFS find ! -size -5 -type f -lazy $dir"
5849         nums=$($cmd | wc -l)
5850         [ $nums -eq $expected ] ||
5851                 error "'$cmd' wrong: found $nums, expected $expected"
5852         cmd="$LFS find ! -size -5 -type f $dir"
5853         nums=$($cmd | wc -l)
5854         [ $nums -eq $expected ] ||
5855                 error "'$cmd' wrong: found $nums, expected $expected"
5856
5857         expected=12
5858         cmd="$LFS find -size -5 -type f -lazy $dir"
5859         nums=$($cmd | wc -l)
5860         [ $nums -eq $expected ] ||
5861                 error "'$cmd' wrong: found $nums, expected $expected"
5862         cmd="$LFS find -size -5 -type f $dir"
5863         nums=$($cmd | wc -l)
5864         [ $nums -eq $expected ] ||
5865                 error "'$cmd' wrong: found $nums, expected $expected"
5866 }
5867 run_test 56r "check lfs find -size works"
5868
5869 test_56ra() {
5870         [[ $MDS1_VERSION -gt $(version_code 2.12.58) ]] ||
5871                 skip "MDS < 2.12.58 doesn't return LSOM data"
5872         local dir=$DIR/$tdir
5873
5874         [[ $OSC == "mdc" ]] && skip "DoM files" && return
5875
5876         setup_56 $dir $NUMFILES $NUMDIRS "-c 1"
5877
5878         cancel_lru_locks $OSC
5879
5880         local rpcs_before=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5881         local expected=12
5882         local cmd="$LFS find -size 0 -type f -lazy $dir"
5883         local nums=$($cmd | wc -l)
5884
5885         [ $nums -eq $expected ] ||
5886                 error "'$cmd' wrong: found $nums, expected $expected"
5887
5888         local rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5889         [ $rpcs_before -eq $rpcs_after ] ||
5890                 error "'$cmd' should not send glimpse RPCs to OST"
5891         cmd="$LFS find -size 0 -type f $dir"
5892         nums=$($cmd | wc -l)
5893         [ $nums -eq $expected ] ||
5894                 error "'$cmd' wrong: found $nums, expected $expected"
5895         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5896         echo "Before: $rpcs_before After: $rpcs_after $NUMFILES"
5897         $LCTL get_param osc.*.stats
5898         [ $rpcs_after -eq $((rpcs_before + 12)) ] ||
5899                 error "'$cmd' should send 12 glimpse RPCs to OST"
5900
5901         cancel_lru_locks $OSC
5902         rpcs_before=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5903         expected=0
5904         cmd="$LFS find ! -size 0 -type f -lazy $dir"
5905         nums=$($cmd | wc -l)
5906         [ $nums -eq $expected ] ||
5907                 error "'$cmd' wrong: found $nums, expected $expected"
5908         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5909         $LCTL get_param mdc.*.stats
5910         [ $rpcs_before -eq $rpcs_after ] ||
5911                 error "'$cmd' should not send glimpse RPCs to OST"
5912         cmd="$LFS find ! -size 0 -type f $dir"
5913         nums=$($cmd | wc -l)
5914         [ $nums -eq $expected ] ||
5915                 error "'$cmd' wrong: found $nums, expected $expected"
5916         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5917         echo "Before: $rpcs_before After: $rpcs_after $NUMFILES"
5918         [ $rpcs_after -eq $((rpcs_before + 12)) ] ||
5919                 error "'$cmd' should send 12 glimpse RPCs to OST"
5920
5921         echo "test" > $dir/$tfile
5922         echo "test2" > $dir/$tfile.2 && sync
5923         cancel_lru_locks $OSC
5924         rpcs_before=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5925         expected=1
5926         cmd="$LFS find -size 5 -type f -lazy $dir"
5927         nums=$($cmd | wc -l)
5928         [ $nums -eq $expected ] ||
5929                 error "'$cmd' wrong: found $nums, expected $expected"
5930         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5931         [ $rpcs_before -eq $rpcs_after ] ||
5932                 error "'$cmd' should not send glimpse RPCs to OST"
5933         cmd="$LFS find -size 5 -type f $dir"
5934         nums=$($cmd | wc -l)
5935         [ $nums -eq $expected ] ||
5936                 error "'$cmd' wrong: found $nums, expected $expected"
5937         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5938         echo "Before: $rpcs_before After: $rpcs_after $NUMFILES"
5939         [ $rpcs_after -eq $((rpcs_before + 14)) ] ||
5940                 error "'$cmd' should send 14 glimpse RPCs to OST"
5941
5942         cancel_lru_locks $OSC
5943         rpcs_before=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5944         expected=1
5945         cmd="$LFS find -size +5 -type f -lazy $dir"
5946         nums=$($cmd | wc -l)
5947         [ $nums -eq $expected ] ||
5948                 error "'$cmd' wrong: found $nums, expected $expected"
5949         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5950         [ $rpcs_before -eq $rpcs_after ] ||
5951                 error "'$cmd' should not send glimpse RPCs to OST"
5952         cmd="$LFS find -size +5 -type f $dir"
5953         nums=$($cmd | wc -l)
5954         [ $nums -eq $expected ] ||
5955                 error "'$cmd' wrong: found $nums, expected $expected"
5956         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5957         echo "Before: $rpcs_before After: $rpcs_after $NUMFILES"
5958         [ $rpcs_after -eq $((rpcs_before + 14)) ] ||
5959                 error "'$cmd' should send 14 glimpse RPCs to OST"
5960
5961         cancel_lru_locks $OSC
5962         rpcs_before=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5963         expected=2
5964         cmd="$LFS find -size +0 -type f -lazy $dir"
5965         nums=$($cmd | wc -l)
5966         [ $nums -eq $expected ] ||
5967                 error "'$cmd' wrong: found $nums, expected $expected"
5968         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5969         [ $rpcs_before -eq $rpcs_after ] ||
5970                 error "'$cmd' should not send glimpse RPCs to OST"
5971         cmd="$LFS find -size +0 -type f $dir"
5972         nums=$($cmd | wc -l)
5973         [ $nums -eq $expected ] ||
5974                 error "'$cmd' wrong: found $nums, expected $expected"
5975         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5976         echo "Before: $rpcs_before After: $rpcs_after $NUMFILES"
5977         [ $rpcs_after -eq $((rpcs_before + 14)) ] ||
5978                 error "'$cmd' should send 14 glimpse RPCs to OST"
5979
5980         cancel_lru_locks $OSC
5981         rpcs_before=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5982         expected=2
5983         cmd="$LFS find ! -size -5 -type f -lazy $dir"
5984         nums=$($cmd | wc -l)
5985         [ $nums -eq $expected ] ||
5986                 error "'$cmd' wrong: found $nums, expected $expected"
5987         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5988         [ $rpcs_before -eq $rpcs_after ] ||
5989                 error "'$cmd' should not send glimpse RPCs to OST"
5990         cmd="$LFS find ! -size -5 -type f $dir"
5991         nums=$($cmd | wc -l)
5992         [ $nums -eq $expected ] ||
5993                 error "'$cmd' wrong: found $nums, expected $expected"
5994         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
5995         echo "Before: $rpcs_before After: $rpcs_after $NUMFILES"
5996         [ $rpcs_after -eq $((rpcs_before + 14)) ] ||
5997                 error "'$cmd' should send 14 glimpse RPCs to OST"
5998
5999         cancel_lru_locks $OSC
6000         rpcs_before=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
6001         expected=12
6002         cmd="$LFS find -size -5 -type f -lazy $dir"
6003         nums=$($cmd | wc -l)
6004         [ $nums -eq $expected ] ||
6005                 error "'$cmd' wrong: found $nums, expected $expected"
6006         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
6007         [ $rpcs_before -eq $rpcs_after ] ||
6008                 error "'$cmd' should not send glimpse RPCs to OST"
6009         cmd="$LFS find -size -5 -type f $dir"
6010         nums=$($cmd | wc -l)
6011         [ $nums -eq $expected ] ||
6012                 error "'$cmd' wrong: found $nums, expected $expected"
6013         rpcs_after=$(calc_stats $OSC.*$OSC*.stats ldlm_glimpse_enqueue)
6014         echo "Before: $rpcs_before After: $rpcs_after $NUMFILES"
6015         [ $rpcs_after -eq $((rpcs_before + 14)) ] ||
6016                 error "'$cmd' should send 14 glimpse RPCs to OST"
6017 }
6018 run_test 56ra "check lfs find -size -lazy works for data on OSTs"
6019
6020 test_56s() { # LU-611 #LU-9369
6021         [[ $OSTCOUNT -lt 2 ]] && skip_env "need at least 2 OSTs"
6022
6023         local dir=$DIR/$tdir
6024         local onestripe=$(((NUMDIRS + 1) * NUMFILES))
6025
6026         setup_56 $dir $NUMFILES $NUMDIRS "-c 1"
6027         for i in $(seq $NUMDIRS); do
6028                 $LFS setstripe -c $((OSTCOUNT + 1)) $dir/dir$i/$tfile
6029         done
6030
6031         local expected=$NUMDIRS
6032         local cmd="$LFS find -c $OSTCOUNT $dir"
6033         local nums=$($cmd | wc -l)
6034
6035         [ $nums -eq $expected ] || {
6036                 $LFS getstripe -R $dir
6037                 error "'$cmd' wrong: found $nums, expected $expected"
6038         }
6039
6040         expected=$((NUMDIRS + onestripe))
6041         cmd="$LFS find -stripe-count +0 -type f $dir"
6042         nums=$($cmd | wc -l)
6043         [ $nums -eq $expected ] || {
6044                 $LFS getstripe -R $dir
6045                 error "'$cmd' wrong: found $nums, expected $expected"
6046         }
6047
6048         expected=$onestripe
6049         cmd="$LFS find -stripe-count 1 -type f $dir"
6050         nums=$($cmd | wc -l)
6051         [ $nums -eq $expected ] || {
6052                 $LFS getstripe -R $dir
6053                 error "'$cmd' wrong: found $nums, expected $expected"
6054         }
6055
6056         cmd="$LFS find -stripe-count -2 -type f $dir"
6057         nums=$($cmd | wc -l)
6058         [ $nums -eq $expected ] || {
6059                 $LFS getstripe -R $dir
6060                 error "'$cmd' wrong: found $nums, expected $expected"
6061         }
6062
6063         expected=0
6064         cmd="$LFS find -stripe-count $((OSTCOUNT + 1)) -type f $dir"
6065         nums=$($cmd | wc -l)
6066         [ $nums -eq $expected ] || {
6067                 $LFS getstripe -R $dir
6068                 error "'$cmd' wrong: found $nums, expected $expected"
6069         }
6070 }
6071 run_test 56s "check lfs find -stripe-count works"
6072
6073 test_56t() { # LU-611 #LU-9369
6074         local dir=$DIR/$tdir
6075
6076         setup_56 $dir 0 $NUMDIRS
6077         for i in $(seq $NUMDIRS); do
6078                 $LFS setstripe -S 8M $dir/dir$i/$tfile
6079         done
6080
6081         local expected=$NUMDIRS
6082         local cmd="$LFS find -S 8M $dir"
6083         local nums=$($cmd | wc -l)
6084
6085         [ $nums -eq $expected ] || {
6086                 $LFS getstripe -R $dir
6087                 error "'$cmd' wrong: found $nums, expected $expected"
6088         }
6089         rm -rf $dir
6090
6091         setup_56 $dir $NUMFILES $NUMDIRS "--stripe-size 512k"
6092
6093         $LFS setstripe -S 256k $dir/$tfile.{0,1,2,3}
6094
6095         expected=$(((NUMDIRS + 1) * NUMFILES))
6096         cmd="$LFS find -stripe-size 512k -type f $dir"
6097         nums=$($cmd | wc -l)
6098         [ $nums -eq $expected ] ||
6099                 error "'$cmd' wrong: found $nums, expected $expected"
6100
6101         cmd="$LFS find -stripe-size +320k -type f $dir"
6102         nums=$($cmd | wc -l)
6103         [ $nums -eq $expected ] ||
6104                 error "'$cmd' wrong: found $nums, expected $expected"
6105
6106         expected=$(((NUMDIRS + 1) * NUMFILES + 4))
6107         cmd="$LFS find -stripe-size +200k -type f $dir"
6108         nums=$($cmd | wc -l)
6109         [ $nums -eq $expected ] ||
6110                 error "'$cmd' wrong: found $nums, expected $expected"
6111
6112         cmd="$LFS find -stripe-size -640k -type f $dir"
6113         nums=$($cmd | wc -l)
6114         [ $nums -eq $expected ] ||
6115                 error "'$cmd' wrong: found $nums, expected $expected"
6116
6117         expected=4
6118         cmd="$LFS find -stripe-size 256k -type f $dir"
6119         nums=$($cmd | wc -l)
6120         [ $nums -eq $expected ] ||
6121                 error "'$cmd' wrong: found $nums, expected $expected"
6122
6123         cmd="$LFS find -stripe-size -320k -type f $dir"
6124         nums=$($cmd | wc -l)
6125         [ $nums -eq $expected ] ||
6126                 error "'$cmd' wrong: found $nums, expected $expected"
6127
6128         expected=0
6129         cmd="$LFS find -stripe-size 1024k -type f $dir"
6130         nums=$($cmd | wc -l)
6131         [ $nums -eq $expected ] ||
6132                 error "'$cmd' wrong: found $nums, expected $expected"
6133 }
6134 run_test 56t "check lfs find -stripe-size works"
6135
6136 test_56u() { # LU-611
6137         local dir=$DIR/$tdir
6138
6139         setup_56 $dir $NUMFILES $NUMDIRS "-i 0 -c 1"
6140
6141         if [[ $OSTCOUNT -gt 1 ]]; then
6142                 $LFS setstripe -i 1 -c 1 $dir/$tfile.{0,1,2,3}
6143                 onestripe=4
6144         else
6145                 onestripe=0
6146         fi
6147
6148         local expected=$(((NUMDIRS + 1) * NUMFILES))
6149         local cmd="$LFS find -stripe-index 0 -type f $dir"
6150         local nums=$($cmd | wc -l)
6151
6152         [ $nums -eq $expected ] ||
6153                 error "'$cmd' wrong: found $nums, expected $expected"
6154
6155         expected=$onestripe
6156         cmd="$LFS find -stripe-index 1 -type f $dir"
6157         nums=$($cmd | wc -l)
6158         [ $nums -eq $expected ] ||
6159                 error "'$cmd' wrong: found $nums, expected $expected"
6160
6161         cmd="$LFS find ! -stripe-index 0 -type f $dir"
6162         nums=$($cmd | wc -l)
6163         [ $nums -eq $expected ] ||
6164                 error "'$cmd' wrong: found $nums, expected $expected"
6165
6166         expected=0
6167         # This should produce an error and not return any files
6168         cmd="$LFS find -stripe-index $OSTCOUNT -type f $dir"
6169         nums=$($cmd 2>/dev/null | wc -l)
6170         [ $nums -eq $expected ] ||
6171                 error "'$cmd' wrong: found $nums, expected $expected"
6172
6173         if [[ $OSTCOUNT -gt 1 ]]; then
6174                 expected=$(((NUMDIRS + 1) * NUMFILES + onestripe))
6175                 cmd="$LFS find -stripe-index 0,1 -type f $dir"
6176                 nums=$($cmd | wc -l)
6177                 [ $nums -eq $expected ] ||
6178                         error "'$cmd' wrong: found $nums, expected $expected"
6179         fi
6180 }
6181 run_test 56u "check lfs find -stripe-index works"
6182
6183 test_56v() {
6184         local mdt_idx=0
6185         local dir=$DIR/$tdir
6186
6187         setup_56 $dir $NUMFILES $NUMDIRS
6188
6189         UUID=$(mdtuuid_from_index $mdt_idx $dir)
6190         [ -z "$UUID" ] && error "mdtuuid_from_index cannot find MDT $mdt_idx"
6191
6192         for file in $($LFS find -m $UUID $dir); do
6193                 file_midx=$($LFS getstripe -m $file)
6194                 [ $file_midx -eq $mdt_idx ] ||
6195                         error "lfs find -m $UUID != getstripe -m $file_midx"
6196         done
6197 }
6198 run_test 56v "check 'lfs find -m match with lfs getstripe -m'"
6199
6200 test_56w() {
6201         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
6202         [ $PARALLEL == "yes" ] && skip "skip parallel run"
6203
6204         local dir=$DIR/$tdir
6205
6206         setup_56 $dir $NUMFILES $NUMDIRS "-c $OSTCOUNT" "-c1"
6207
6208         local stripe_size=$($LFS getstripe -S -d $dir) ||
6209                 error "$LFS getstripe -S -d $dir failed"
6210         stripe_size=${stripe_size%% *}
6211
6212         local file_size=$((stripe_size * OSTCOUNT))
6213         local file_num=$((NUMDIRS * NUMFILES + NUMFILES))
6214         local required_space=$((file_num * file_size))
6215         local free_space=$($LCTL get_param -n lov.$FSNAME-clilov-*.kbytesavail |
6216                            head -n1)
6217         [[ $free_space -le $((required_space / 1024)) ]] &&
6218                 skip_env "need $required_space, have $free_space kbytes"
6219
6220         local dd_bs=65536
6221         local dd_count=$((file_size / dd_bs))
6222
6223         # write data into the files
6224         local i
6225         local j
6226         local file
6227
6228         for i in $(seq $NUMFILES); do
6229                 file=$dir/file$i
6230                 yes | dd bs=$dd_bs count=$dd_count of=$file &>/dev/null ||
6231                         error "write data into $file failed"
6232         done
6233         for i in $(seq $NUMDIRS); do
6234                 for j in $(seq $NUMFILES); do
6235                         file=$dir/dir$i/file$j
6236                         yes|dd bs=$dd_bs count=$dd_count of=$file &>/dev/null ||
6237                                 error "write data into $file failed"
6238                 done
6239         done
6240
6241         # $LFS_MIGRATE will fail if hard link migration is unsupported
6242         if [[ $MDS1_VERSION -gt $(version_code 2.5.55) ]]; then
6243                 createmany -l$dir/dir1/file1 $dir/dir1/link 200 ||
6244                         error "creating links to $dir/dir1/file1 failed"
6245         fi
6246
6247         local expected=-1
6248
6249         [[ $OSTCOUNT -gt 1 ]] && expected=$((OSTCOUNT - 1))
6250
6251         # lfs_migrate file
6252         local cmd="$LFS_MIGRATE -y -c $expected $dir/file1"
6253
6254         echo "$cmd"
6255         eval $cmd || error "$cmd failed"
6256
6257         check_stripe_count $dir/file1 $expected
6258
6259         if [ $MDS1_VERSION -ge $(version_code 2.6.90) ];
6260         then
6261                 # lfs_migrate file onto OST 0 if it is on OST 1, or onto
6262                 # OST 1 if it is on OST 0. This file is small enough to
6263                 # be on only one stripe.
6264                 file=$dir/migr_1_ost
6265                 dd bs=$dd_bs count=1 if=/dev/urandom of=$file >/dev/null 2>&1 ||
6266                         error "write data into $file failed"
6267                 local obdidx=$($LFS getstripe -i $file)
6268                 local oldmd5=$(md5sum $file)
6269                 local newobdidx=0
6270
6271                 [[ $obdidx -eq 0 ]] && newobdidx=1
6272                 cmd="$LFS migrate -i $newobdidx $file"
6273                 echo $cmd
6274                 eval $cmd || error "$cmd failed"
6275
6276                 local realobdix=$($LFS getstripe -i $file)
6277                 local newmd5=$(md5sum $file)
6278
6279                 [[ $newobdidx -ne $realobdix ]] &&
6280                         error "new OST is different (was=$obdidx, "\
6281                               "wanted=$newobdidx, got=$realobdix)"
6282                 [[ "$oldmd5" != "$newmd5" ]] &&
6283                         error "md5sum differ: $oldmd5, $newmd5"
6284         fi
6285
6286         # lfs_migrate dir
6287         cmd="$LFS_MIGRATE -y -c $expected $dir/dir1"
6288         echo "$cmd"
6289         eval $cmd || error "$cmd failed"
6290
6291         for j in $(seq $NUMFILES); do
6292                 check_stripe_count $dir/dir1/file$j $expected
6293         done
6294
6295         # lfs_migrate works with lfs find
6296         cmd="$LFS find -stripe_count $OSTCOUNT -type f $dir |
6297              $LFS_MIGRATE -y -c $expected"
6298         echo "$cmd"
6299         eval $cmd || error "$cmd failed"
6300
6301         for i in $(seq 2 $NUMFILES); do
6302                 check_stripe_count $dir/file$i $expected
6303         done
6304         for i in $(seq 2 $NUMDIRS); do
6305                 for j in $(seq $NUMFILES); do
6306                 check_stripe_count $dir/dir$i/file$j $expected
6307                 done
6308         done
6309 }
6310 run_test 56w "check lfs_migrate -c stripe_count works"
6311
6312 test_56wb() {
6313         local file1=$DIR/$tdir/file1
6314         local create_pool=false
6315         local initial_pool=$($LFS getstripe -p $DIR)
6316         local pool_list=()
6317         local pool=""
6318
6319         echo -n "Creating test dir..."
6320         test_mkdir $DIR/$tdir &> /dev/null || error "cannot create dir"
6321         echo "done."
6322
6323         echo -n "Creating test file..."
6324         touch $file1 || error "cannot create file"
6325         echo "done."
6326
6327         echo -n "Detecting existing pools..."
6328         pool_list=($($LFS pool_list $FSNAME | grep "$FSNAME\." | cut -d. -f2))
6329
6330         if [ ${#pool_list[@]} -gt 0 ]; then
6331                 echo "${pool_list[@]}"
6332                 for thispool in "${pool_list[@]}"; do
6333                         if [[ -z "$initial_pool" ||
6334                               "$initial_pool" != "$thispool" ]]; then
6335                                 pool="$thispool"
6336                                 echo "Using existing pool '$pool'"
6337                                 break
6338                         fi
6339                 done
6340         else
6341                 echo "none detected."
6342         fi
6343         if [ -z "$pool" ]; then
6344                 pool=${POOL:-testpool}
6345                 [ "$initial_pool" = "$pool" ] && pool="testpool2"
6346                 echo -n "Creating pool '$pool'..."
6347                 create_pool=true
6348                 pool_add $pool &> /dev/null ||
6349                         error "pool_add failed"
6350                 echo "done."
6351
6352                 echo -n "Adding target to pool..."
6353                 pool_add_targets $pool 0 0 1 &> /dev/null ||
6354                         error "pool_add_targets failed"
6355                 echo "done."
6356         fi
6357
6358         echo -n "Setting pool using -p option..."
6359         $LFS_MIGRATE -y -q --no-rsync -p $pool $file1 &> /dev/null ||
6360                 error "migrate failed rc = $?"
6361         echo "done."
6362
6363         echo -n "Verifying test file is in pool after migrating..."
6364         [ "$($LFS getstripe -p $file1)" = $pool ] ||
6365                 error "file was not migrated to pool $pool"
6366         echo "done."
6367
6368         echo -n "Removing test file from pool '$pool'..."
6369         $LFS migrate $file1 &> /dev/null ||
6370                 error "cannot remove from pool"
6371         [ "$($LFS getstripe -p $file1)" ] &&
6372                 error "pool still set"
6373         echo "done."
6374
6375         echo -n "Setting pool using --pool option..."
6376         $LFS_MIGRATE -y -q --no-rsync --pool $pool $file1 &> /dev/null ||
6377                 error "migrate failed rc = $?"
6378         echo "done."
6379
6380         # Clean up
6381         rm -f $file1
6382         if $create_pool; then
6383                 destroy_test_pools 2> /dev/null ||
6384                         error "destroy test pools failed"
6385         fi
6386 }
6387 run_test 56wb "check lfs_migrate pool support"
6388
6389 test_56wc() {
6390         local file1="$DIR/$tdir/file1"
6391
6392         echo -n "Creating test dir..."
6393         test_mkdir $DIR/$tdir &> /dev/null || error "cannot create dir"
6394         local def_stripe_size=$($LFS getstripe -S $DIR/$tdir 2>/dev/null)
6395         $LFS setstripe -S 1M -c 1 "$DIR/$tdir" &> /dev/null ||
6396                 error "cannot set stripe"
6397         echo "done"
6398
6399         echo -n "Setting initial stripe for test file..."
6400         $LFS setstripe -S 512K -c 1 "$file1" &> /dev/null ||
6401                 error "cannot set stripe"
6402         [ $($LFS getstripe -S "$file1") -eq 524288 ] ||
6403                 error "stripe size not set"
6404         echo "done."
6405
6406         # File currently set to -S 512K -c 1
6407
6408         # Ensure -c and -S options are rejected when -R is set
6409         echo -n "Verifying incompatible options are detected..."
6410         $LFS_MIGRATE -y -R -c 1 "$file1" &> /dev/null &&
6411                 error "incompatible -c and -R options not detected"
6412         $LFS_MIGRATE -y -R -S 1M "$file1" &> /dev/null &&
6413                 error "incompatible -S and -R options not detected"
6414         echo "done."
6415
6416         # Ensure unrecognized options are passed through to 'lfs migrate'
6417         echo -n "Verifying -S option is passed through to lfs migrate..."
6418         $LFS_MIGRATE -y -S 1M "$file1" &> /dev/null ||
6419                 error "migration failed"
6420         [ $($LFS getstripe -S "$file1") -eq 1048576 ] ||
6421                 error "file was not restriped"
6422         echo "done."
6423
6424         # File currently set to -S 1M -c 1
6425
6426         # Ensure long options are supported
6427         echo -n "Verifying long options supported..."
6428         $LFS_MIGRATE -y --non-block "$file1" &> /dev/null ||
6429                 error "long option without argument not supported"
6430         $LFS_MIGRATE -y --stripe-size 512K "$file1" &> /dev/null ||
6431                 error "long option with argument not supported"
6432         [ $($LFS getstripe -S "$file1") -eq 524288 ] ||
6433                 error "file not restriped with --stripe-size option"
6434         echo "done."
6435
6436         # File currently set to -S 512K -c 1
6437
6438         if [ "$OSTCOUNT" -gt 1 ]; then
6439                 echo -n "Verifying explicit stripe count can be set..."
6440                 $LFS_MIGRATE -y -c 2 "$file1" &> /dev/null ||
6441                         error "migrate failed"
6442                 [ $($LFS getstripe -c "$file1") -eq 2 ] ||
6443                         error "file not restriped to explicit count"
6444                 echo "done."
6445         fi
6446
6447         # File currently set to -S 512K -c 1 or -S 512K -c 2
6448
6449         # Ensure parent striping is used if -R is set, and no stripe
6450         # count or size is specified
6451         echo -n "Setting stripe for parent directory..."
6452         $LFS setstripe -S 1M -c 1 "$DIR/$tdir" &> /dev/null ||
6453                 error "cannot set stripe"
6454         echo "done."
6455
6456         echo -n "Verifying restripe option uses parent stripe settings..."
6457         $LFS_MIGRATE -y -R "$file1" &> /dev/null ||
6458                 error "migrate failed"
6459         [ $($LFS getstripe -S "$file1") -eq $def_stripe_size ] ||
6460                 error "file not restriped to parent settings"
6461         [ $($LFS getstripe -c "$file1") -eq 1 ] ||
6462                 error "file not restriped to parent settings"
6463         echo "done."
6464
6465         # File currently set to -S 1M -c 1
6466
6467         # Ensure striping is preserved if -R is not set, and no stripe
6468         # count or size is specified
6469         echo -n "Verifying striping size preserved when not specified..."
6470         local orig_stripe_size=$($LFS getstripe -S "$file1" 2>/dev/null)
6471         $LFS setstripe -S 2M -c 1 "$DIR/$tdir" &> /dev/null ||
6472                 error "cannot set stripe on parent directory"
6473         $LFS_MIGRATE -y "$file1" &> /dev/null ||
6474                 error "migrate failed"
6475         [ $($LFS getstripe -S "$file1") -eq $orig_stripe_size ] ||
6476                 error "file was restriped"
6477         echo "done."
6478
6479         # Ensure file name properly detected when final option has no argument
6480         echo -n "Verifying file name properly detected..."
6481         $LFS_MIGRATE -y "$file1" &> /dev/null ||
6482                 error "file name interpreted as option argument"
6483         echo "done."
6484
6485         # Clean up
6486         rm -f "$file1"
6487 }
6488 run_test 56wc "check unrecognized options for lfs_migrate are passed through"
6489
6490 test_56wd() {
6491         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
6492
6493         local file1=$DIR/$tdir/file1
6494
6495         echo -n "Creating test dir..."
6496         test_mkdir $DIR/$tdir || error "cannot create dir"
6497         echo "done."
6498
6499         echo -n "Creating test file..."
6500         touch $file1
6501         echo "done."
6502
6503         # Ensure 'lfs migrate' will fail by using a non-existent option,
6504         # and make sure rsync is not called to recover
6505         echo -n "Make sure --no-rsync option works..."
6506         $LFS_MIGRATE -y --no-rsync --invalid-opt $file1 2>&1 |
6507                 grep -q 'refusing to fall back to rsync' ||
6508                 error "rsync was called with --no-rsync set"
6509         echo "done."
6510
6511         # Ensure rsync is called without trying 'lfs migrate' first
6512         echo -n "Make sure --rsync option works..."
6513         $LFS_MIGRATE -y --rsync --invalid-opt $file1 2>&1 |
6514                 grep -q 'falling back to rsync' &&
6515                 error "lfs migrate was called with --rsync set"
6516         echo "done."
6517
6518         echo -n "Make sure --rsync and --no-rsync options are exclusive..."
6519         $LFS_MIGRATE -y --rsync --no-rsync $file1 2>&1 |
6520                 grep -q 'at the same time' ||
6521                 error "--rsync and --no-rsync accepted concurrently"
6522         echo "done."
6523
6524         # Clean up
6525         rm -f $file1
6526 }
6527 run_test 56wd "check lfs_migrate --rsync and --no-rsync work"
6528
6529 test_56x() {
6530         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
6531         check_swap_layouts_support
6532
6533         local dir=$DIR/$tdir
6534         local ref1=/etc/passwd
6535         local file1=$dir/file1
6536
6537         test_mkdir $dir || error "creating dir $dir"
6538         $LFS setstripe -c 2 $file1
6539         cp $ref1 $file1
6540         $LFS migrate -c 1 $file1 || error "migrate failed rc = $?"
6541         stripe=$($LFS getstripe -c $file1)
6542         [[ $stripe == 1 ]] || error "stripe of $file1 is $stripe != 1"
6543         cmp $file1 $ref1 || error "content mismatch $file1 differs from $ref1"
6544
6545         # clean up
6546         rm -f $file1
6547 }
6548 run_test 56x "lfs migration support"
6549
6550 test_56xa() {
6551         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
6552         check_swap_layouts_support
6553
6554         local dir=$DIR/$tdir/$testnum
6555
6556         test_mkdir -p $dir
6557
6558         local ref1=/etc/passwd
6559         local file1=$dir/file1
6560
6561         $LFS setstripe -c 2 $file1
6562         cp $ref1 $file1
6563         $LFS migrate --block -c 1 $file1 || error "migrate failed rc = $?"
6564
6565         local stripe=$($LFS getstripe -c $file1)
6566
6567         [[ $stripe == 1 ]] || error "stripe of $file1 is $stripe != 1"
6568         cmp $file1 $ref1 || error "content mismatch $file1 differs from $ref1"
6569
6570         # clean up
6571         rm -f $file1
6572 }
6573 run_test 56xa "lfs migration --block support"
6574
6575 check_migrate_links() {
6576         local dir="$1"
6577         local file1="$dir/file1"
6578         local begin="$2"
6579         local count="$3"
6580         local runas="$4"
6581         local total_count=$(($begin + $count - 1))
6582         local symlink_count=10
6583         local uniq_count=10
6584
6585         if [ ! -f "$file1" ]; then
6586                 echo -n "creating initial file..."
6587                 $LFS setstripe -c 1 -S "512k" "$file1" ||
6588                         error "cannot setstripe initial file"
6589                 echo "done"
6590
6591                 echo -n "creating symlinks..."
6592                 for s in $(seq 1 $symlink_count); do
6593                         ln -s "$file1" "$dir/slink$s" ||
6594                                 error "cannot create symlinks"
6595                 done
6596                 echo "done"
6597
6598                 echo -n "creating nonlinked files..."
6599                 createmany -o "$dir/uniq" 1 10 &> /dev/null ||
6600                         error "cannot create nonlinked files"
6601                 echo "done"
6602         fi
6603
6604         # create hard links
6605         if [ ! -f "$dir/file$total_count" ]; then
6606                 echo -n "creating hard links $begin:$total_count..."
6607                 createmany -l"$file1" "$dir/file" "$begin" "$count" &>  \
6608                         /dev/null || error "cannot create hard links"
6609                 echo "done"
6610         fi
6611
6612         echo -n "checking number of hard links listed in xattrs..."
6613         local fid=$($LFS getstripe -F "$file1")
6614         local paths=($($LFS fid2path "$MOUNT" "$fid" 2> /dev/null))
6615
6616         echo "${#paths[*]}"
6617         if [ ${#paths[*]} -lt $total_count -a "$begin" -eq 2  ]; then
6618                         skip "hard link list has unexpected size, skipping test"
6619         fi
6620         if [ ${#paths[*]} -ge $total_count -a "$begin" -ne 2  ]; then
6621                         error "link names should exceed xattrs size"
6622         fi
6623
6624         echo -n "migrating files..."
6625         local migrate_out=$($runas $LFS_MIGRATE -y -S '1m' $dir)
6626         local rc=$?
6627         [ $rc -eq 0 ] || error "migrate failed rc = $rc"
6628         echo "done"
6629
6630         # make sure all links have been properly migrated
6631         echo -n "verifying files..."
6632         fid=$($LFS getstripe -F "$file1") ||
6633                 error "cannot get fid for file $file1"
6634         for i in $(seq 2 $total_count); do
6635                 local fid2=$($LFS getstripe -F $dir/file$i)
6636
6637                 [ "$fid2" == "$fid" ] ||
6638                         error "migrated hard link has mismatched FID"
6639         done
6640
6641         # make sure hard links were properly detected, and migration was
6642         # performed only once for the entire link set; nonlinked files should
6643         # also be migrated
6644         local actual=$(grep -c 'done' <<< "$migrate_out")
6645         local expected=$(($uniq_count + 1))
6646
6647         [ "$actual" -eq  "$expected" ] ||
6648                 error "hard links individually migrated ($actual != $expected)"
6649
6650         # make sure the correct number of hard links are present
6651         local hardlinks=$(stat -c '%h' "$file1")
6652
6653         [ $hardlinks -eq $total_count ] ||
6654                 error "num hard links $hardlinks != $total_count"
6655         echo "done"
6656
6657         return 0
6658 }
6659
6660 test_56xb() {
6661         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
6662                 skip "Need MDS version at least 2.10.55"
6663
6664         local dir="$DIR/$tdir"
6665
6666         test_mkdir "$dir" || error "cannot create dir $dir"
6667
6668         echo "testing lfs migrate mode when all links fit within xattrs"
6669         LFS_MIGRATE_RSYNC_MODE=false check_migrate_links "$dir" 2 99
6670
6671         echo "testing rsync mode when all links fit within xattrs"
6672         LFS_MIGRATE_RSYNC_MODE=true check_migrate_links "$dir" 2 99
6673
6674         echo "testing lfs migrate mode when all links do not fit within xattrs"
6675         LFS_MIGRATE_RSYNC_MODE=false check_migrate_links "$dir" 101 100
6676
6677         echo "testing rsync mode when all links do not fit within xattrs"
6678         LFS_MIGRATE_RSYNC_MODE=true check_migrate_links "$dir" 101 100
6679
6680         chown -R $RUNAS_ID $dir
6681         echo "testing non-root lfs migrate mode when not all links are in xattr"
6682         LFS_MIGRATE_RSYNC_MODE=false check_migrate_links "$dir" 101 100 "$RUNAS"
6683
6684         # clean up
6685         rm -rf $dir
6686 }
6687 run_test 56xb "lfs migration hard link support"
6688
6689 test_56xc() {
6690         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
6691
6692         local dir="$DIR/$tdir"
6693
6694         test_mkdir "$dir" || error "cannot create dir $dir"
6695
6696         # Test 1: ensure file < 1 GB is always migrated with 1 stripe
6697         echo -n "Setting initial stripe for 20MB test file..."
6698         $LFS setstripe -c 2 -i 0 "$dir/20mb" ||
6699                 error "cannot setstripe 20MB file"
6700         echo "done"
6701         echo -n "Sizing 20MB test file..."
6702         truncate "$dir/20mb" 20971520 || error "cannot create 20MB test file"
6703         echo "done"
6704         echo -n "Verifying small file autostripe count is 1..."
6705         $LFS_MIGRATE -y -A -C 1 "$dir/20mb" ||
6706                 error "cannot migrate 20MB file"
6707         local stripe_count=$($LFS getstripe -c "$dir/20mb") ||
6708                 error "cannot get stripe for $dir/20mb"
6709         [ $stripe_count -eq 1 ] ||
6710                 error "unexpected stripe count $stripe_count for 20MB file"
6711         rm -f "$dir/20mb"
6712         echo "done"
6713
6714         # Test 2: File is small enough to fit within the available space on
6715         # sqrt(size_in_gb) + 1 OSTs but is larger than 1GB.  The file must
6716         # have at least an additional 1KB for each desired stripe for test 3
6717         echo -n "Setting stripe for 1GB test file..."
6718         $LFS setstripe -c 1 -i 0 "$dir/1gb" || error "cannot setstripe 1GB file"
6719         echo "done"
6720         echo -n "Sizing 1GB test file..."
6721         # File size is 1GB + 3KB
6722         truncate "$dir/1gb" 1073744896 || error "cannot create 1GB test file"
6723         echo "done"
6724
6725         # need at least 512MB per OST for 1GB file to fit in 2 stripes
6726         local avail=$($LCTL get_param -n llite.$FSNAME*.kbytesavail)
6727         if (( avail > 524288 * OSTCOUNT )); then
6728                 echo -n "Migrating 1GB file..."
6729                 $LFS_MIGRATE -y -A -C 1 "$dir/1gb" ||
6730                         error "cannot migrate 1GB file"
6731                 echo "done"
6732                 echo -n "Verifying autostripe count is sqrt(n) + 1..."
6733                 stripe_count=$($LFS getstripe -c "$dir/1gb") ||
6734                         error "cannot getstripe for 1GB file"
6735                 [ $stripe_count -eq 2 ] ||
6736                         error "unexpected stripe count $stripe_count != 2"
6737                 echo "done"
6738         fi
6739
6740         # Test 3: File is too large to fit within the available space on
6741         # sqrt(n) + 1 OSTs.  Simulate limited available space with -X
6742         if [ $OSTCOUNT -ge 3 ]; then
6743                 # The required available space is calculated as
6744                 # file size (1GB + 3KB) / OST count (3).
6745                 local kb_per_ost=349526
6746
6747                 echo -n "Migrating 1GB file with limit..."
6748                 $LFS_MIGRATE -y -A -C 1 -X $kb_per_ost "$dir/1gb" ||
6749                         error "cannot migrate 1GB file with limit"
6750                 echo "done"
6751
6752                 stripe_count=$($LFS getstripe -c "$dir/1gb")
6753                 echo -n "Verifying 1GB autostripe count with limited space..."
6754                 [ "$stripe_count" -a $stripe_count -ge 3 ] ||
6755                         error "unexpected stripe count $stripe_count (min 3)"
6756                 echo "done"
6757         fi
6758
6759         # clean up
6760         rm -rf $dir
6761 }
6762 run_test 56xc "lfs migration autostripe"
6763
6764 test_56y() {
6765         [ $MDS1_VERSION -lt $(version_code 2.4.53) ] &&
6766                 skip "No HSM $(lustre_build_version $SINGLEMDS) MDS < 2.4.53"
6767
6768         local res=""
6769         local dir=$DIR/$tdir
6770         local f1=$dir/file1
6771         local f2=$dir/file2
6772
6773         test_mkdir -p $dir || error "creating dir $dir"
6774         touch $f1 || error "creating std file $f1"
6775         $MULTIOP $f2 H2c || error "creating released file $f2"
6776
6777         # a directory can be raid0, so ask only for files
6778         res=$($LFS find $dir -L raid0 -type f | wc -l)
6779         [[ $res == 2 ]] || error "search raid0: found $res files != 2"
6780
6781         res=$($LFS find $dir \! -L raid0 -type f | wc -l)
6782         [[ $res == 0 ]] || error "search !raid0: found $res files != 0"
6783
6784         # only files can be released, so no need to force file search
6785         res=$($LFS find $dir -L released)
6786         [[ $res == $f2 ]] || error "search released: found $res != $f2"
6787
6788         res=$($LFS find $dir -type f \! -L released)
6789         [[ $res == $f1 ]] || error "search !released: found $res != $f1"
6790 }
6791 run_test 56y "lfs find -L raid0|released"
6792
6793 test_56z() { # LU-4824
6794         # This checks to make sure 'lfs find' continues after errors
6795         # There are two classes of errors that should be caught:
6796         # - If multiple paths are provided, all should be searched even if one
6797         #   errors out
6798         # - If errors are encountered during the search, it should not terminate
6799         #   early
6800         local dir=$DIR/$tdir
6801         local i
6802
6803         test_mkdir $dir
6804         for i in d{0..9}; do
6805                 test_mkdir $dir/$i
6806                 touch $dir/$i/$tfile
6807         done
6808         $LFS find $DIR/non_existent_dir $dir &&
6809                 error "$LFS find did not return an error"
6810         # Make a directory unsearchable. This should NOT be the last entry in
6811         # directory order.  Arbitrarily pick the 6th entry
6812         chmod 700 $($LFS find $dir -type d | sed '6!d')
6813
6814         $RUNAS $LFS find $DIR/non_existent $dir
6815         local count=$($RUNAS $LFS find $DIR/non_existent $dir | wc -l)
6816
6817         # The user should be able to see 10 directories and 9 files
6818         (( count == 19 )) ||
6819                 error "$LFS find found $count != 19 entries after error"
6820 }
6821 run_test 56z "lfs find should continue after an error"
6822
6823 test_56aa() { # LU-5937
6824         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
6825
6826         local dir=$DIR/$tdir
6827
6828         mkdir $dir
6829         $LFS setdirstripe -c$MDSCOUNT $dir/striped_dir
6830
6831         createmany -o $dir/striped_dir/${tfile}- 1024
6832         local dirs=$($LFS find --size +8k $dir/)
6833
6834         [ -n "$dirs" ] || error "lfs find --size wrong under striped dir"
6835 }
6836 run_test 56aa "lfs find --size under striped dir"
6837
6838 test_56ab() { # LU-10705
6839         test_mkdir $DIR/$tdir
6840         dd if=/dev/zero of=$DIR/$tdir/$tfile.1 bs=8k count=1 seek=2k
6841         dd if=/dev/zero of=$DIR/$tdir/$tfile.2 bs=4k count=1 seek=4k
6842         dd if=/dev/zero of=$DIR/$tdir/$tfile.3 bs=1M count=2 seek=16
6843         # Flush writes to ensure valid blocks.  Need to be more thorough for
6844         # ZFS, since blocks are not allocated/returned to client immediately.
6845         sync_all_data
6846         wait_zfs_commit ost1 2
6847         cancel_lru_locks osc
6848         ls -ls $DIR/$tdir
6849
6850         local files=$($LFS find --size +16M $DIR/$tdir | wc -l)
6851
6852         [[ $files == 3 ]] || error ">16M size files $files isn't 3 as expected"
6853
6854         files=$($LFS find --blocks +1M $DIR/$tdir | wc -l)
6855         [[ $files == 1 ]] || error ">1M blocks files $files isn't 1 as expected"
6856
6857         rm -f $DIR/$tdir/$tfile.[123]
6858 }
6859 run_test 56ab "lfs find --blocks"
6860
6861 test_56ba() {
6862         [ $MDS1_VERSION -lt $(version_code 2.10.50) ] &&
6863                 skip "Need MDS version at least 2.10.50"
6864
6865         # Create composite files with one component
6866         local dir=$DIR/$tdir
6867
6868         setup_56 $dir/1Mfiles 5 1 "-S 1M --component-end 1M"
6869         # Create composite files with three components
6870         setup_56 $dir/2Mfiles 5 2 "-E 2M -S 1M -E 4M -E 6M"
6871         # Create non-composite files
6872         createmany -o $dir/${tfile}- 10
6873
6874         local nfiles=$($LFS find --component-end 1M --type f $dir | wc -l)
6875
6876         [[ $nfiles == 10 ]] ||
6877                 error "lfs find -E 1M found $nfiles != 10 files"
6878
6879         nfiles=$($LFS find ! -E 1M --type f $dir | wc -l)
6880         [[ $nfiles == 25 ]] ||
6881                 error "lfs find ! -E 1M found $nfiles != 25 files"
6882
6883         # All files have a component that starts at 0
6884         nfiles=$($LFS find --component-start 0 --type f $dir | wc -l)
6885         [[ $nfiles == 35 ]] ||
6886                 error "lfs find --component-start 0 - $nfiles != 35 files"
6887
6888         nfiles=$($LFS find --component-start 2M --type f $dir | wc -l)
6889         [[ $nfiles == 15 ]] ||
6890                 error "lfs find --component-start 2M - $nfiles != 15 files"
6891
6892         # All files created here have a componenet that does not starts at 2M
6893         nfiles=$($LFS find ! --component-start 2M --type f $dir | wc -l)
6894         [[ $nfiles == 35 ]] ||
6895                 error "lfs find ! --component-start 2M - $nfiles != 35 files"
6896
6897         # Find files with a specified number of components
6898         local nfiles=$($LFS find --component-count 3 --type f $dir | wc -l)
6899         [[ $nfiles == 15 ]] ||
6900                 error "lfs find --component-count 3 - $nfiles != 15 files"
6901
6902         # Remember non-composite files have a component count of zero
6903         local nfiles=$($LFS find --component-count 0 --type f $dir | wc -l)
6904         [[ $nfiles == 10 ]] ||
6905                 error "lfs find --component-count 0 - $nfiles != 10 files"
6906
6907         nfiles=$($LFS find ! --component-count 3 --type f $dir | wc -l)
6908         [[ $nfiles == 20 ]] ||
6909                 error "lfs find ! --component-count 3 - $nfiles != 20 files"
6910
6911         # All files have a flag called "init"
6912         local nfiles=$($LFS find --component-flags init --type f $dir | wc -l)
6913         [[ $nfiles == 35 ]] ||
6914                 error "lfs find --component-flags init - $nfiles != 35 files"
6915
6916         # Multi-component files will have a component not initialized
6917         local nfiles=$($LFS find ! --component-flags init --type f $dir | wc -l)
6918         [[ $nfiles == 15 ]] ||
6919                 error "lfs find !--component-flags init - $nfiles != 15 files"
6920
6921         rm -rf $dir
6922
6923 }
6924 run_test 56ba "test lfs find --component-end, -start, -count, and -flags"
6925
6926 test_56ca() {
6927         [[ $MDS1_VERSION -ge $(version_code 2.10.57) ]] ||
6928                 skip "Need MDS version at least 2.10.57"
6929
6930         local td=$DIR/$tdir
6931         local tf=$td/$tfile
6932         local dir
6933         local nfiles
6934         local cmd
6935         local i
6936         local j
6937
6938         # create mirrored directories and mirrored files
6939         mkdir $td || error "mkdir $td failed"
6940         $LFS mirror create -N3 $td || error "create mirrored dir $td failed"
6941         createmany -o $tf- 10 || error "create $tf- failed"
6942
6943         for i in $(seq 2); do
6944                 dir=$td/dir$i
6945                 mkdir $dir || error "mkdir $dir failed"
6946                 $LFS mirror create -N$((3 + i)) $dir ||
6947                         error "create mirrored dir $dir failed"
6948                 createmany -o $dir/$tfile- 10 ||
6949                         error "create $dir/$tfile- failed"
6950         done
6951
6952         # change the states of some mirrored files
6953         echo foo > $tf-6
6954         for i in $(seq 2); do
6955                 dir=$td/dir$i
6956                 for j in $(seq 4 9); do
6957                         echo foo > $dir/$tfile-$j
6958                 done
6959         done
6960
6961         # find mirrored files with specific mirror count
6962         cmd="$LFS find --mirror-count 3 --type f $td"
6963         nfiles=$($cmd | wc -l)
6964         [[ $nfiles = 10 ]] || error "$cmd: $nfiles != 10 files"
6965
6966         cmd="$LFS find ! --mirror-count 3 --type f $td"
6967         nfiles=$($cmd | wc -l)
6968         [[ $nfiles = 20 ]] || error "$cmd: $nfiles != 20 files"
6969
6970         cmd="$LFS find --mirror-count +2 --type f $td"
6971         nfiles=$($cmd | wc -l)
6972         [[ $nfiles = 30 ]] || error "$cmd: $nfiles != 30 files"
6973
6974         cmd="$LFS find --mirror-count -6 --type f $td"
6975         nfiles=$($cmd | wc -l)
6976         [[ $nfiles = 30 ]] || error "$cmd: $nfiles != 30 files"
6977
6978         # find mirrored files with specific file state
6979         cmd="$LFS find --maxdepth 1 --mirror-state=^ro --type f $td"
6980         [[ $($cmd) = $tf-6 ]] || error "$cmd: didn't return $tf-6"
6981
6982         cmd="$LFS find --mirror-state=ro --type f $td"
6983         nfiles=$($cmd | wc -l)
6984         [[ $nfiles = 17 ]] || error "$cmd: $nfiles != 17 files"
6985
6986         cmd="$LFS find ! --mirror-state=ro --type f $td"
6987         nfiles=$($cmd | wc -l)
6988         [[ $nfiles = 13 ]] || error "$cmd: $nfiles != 13 files"
6989
6990         cmd="$LFS find --mirror-state=wp --type f $td"
6991         nfiles=$($cmd | wc -l)
6992         [[ $nfiles = 13 ]] || error "$cmd: $nfiles != 13 files"
6993
6994         cmd="$LFS find ! --mirror-state=sp --type f $td"
6995         nfiles=$($cmd | wc -l)
6996         [[ $nfiles = 30 ]] || error "$cmd: $nfiles != 30 files"
6997 }
6998 run_test 56ca "check lfs find --mirror-count|-N and --mirror-state"
6999
7000 test_57a() {
7001         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7002         # note test will not do anything if MDS is not local
7003         if [ "$mds1_FSTYPE" != ldiskfs ]; then
7004                 skip_env "ldiskfs only test"
7005         fi
7006         remote_mds_nodsh && skip "remote MDS with nodsh"
7007
7008         local MNTDEV="osd*.*MDT*.mntdev"
7009         DEV=$(do_facet $SINGLEMDS lctl get_param -n $MNTDEV)
7010         [ -z "$DEV" ] && error "can't access $MNTDEV"
7011         for DEV in $(do_facet $SINGLEMDS lctl get_param -n $MNTDEV); do
7012                 do_facet $SINGLEMDS $DUMPE2FS -h $DEV > $TMP/t57a.dump ||
7013                         error "can't access $DEV"
7014                 DEVISIZE=$(awk '/Inode size:/ { print $3 }' $TMP/t57a.dump)
7015                 [[ $DEVISIZE -gt 128 ]] || error "inode size $DEVISIZE"
7016                 rm $TMP/t57a.dump
7017         done
7018 }
7019 run_test 57a "verify MDS filesystem created with large inodes =="
7020
7021 test_57b() {
7022         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7023         if [ "$mds1_FSTYPE" != ldiskfs ]; then
7024                 skip_env "ldiskfs only test"
7025         fi
7026         remote_mds_nodsh && skip "remote MDS with nodsh"
7027
7028         local dir=$DIR/$tdir
7029         local filecount=100
7030         local file1=$dir/f1
7031         local fileN=$dir/f$filecount
7032
7033         rm -rf $dir || error "removing $dir"
7034         test_mkdir -c1 $dir
7035         local mdtidx=$($LFS getstripe -m $dir)
7036         local mdtname=MDT$(printf %04x $mdtidx)
7037         local facet=mds$((mdtidx + 1))
7038
7039         echo "mcreating $filecount files"
7040         createmany -m $dir/f 1 $filecount || error "creating files in $dir"
7041
7042         # verify that files do not have EAs yet
7043         $LFS getstripe $file1 2>&1 | grep -q "no stripe" ||
7044                 error "$file1 has an EA"
7045         $LFS getstripe $fileN 2>&1 | grep -q "no stripe" ||
7046                 error "$fileN has an EA"
7047
7048         sync
7049         sleep 1
7050         df $dir  #make sure we get new statfs data
7051         local mdsfree=$(do_facet $facet \
7052                         lctl get_param -n osd*.*$mdtname.kbytesfree)
7053         local mdcfree=$(lctl get_param -n mdc.*$mdtname-mdc-*.kbytesfree)
7054         local file
7055
7056         echo "opening files to create objects/EAs"
7057         for file in $(seq -f $dir/f%g 1 $filecount); do
7058                 $OPENFILE -f O_RDWR $file > /dev/null 2>&1 ||
7059                         error "opening $file"
7060         done
7061
7062         # verify that files have EAs now
7063         $LFS getstripe $file1 | grep -q "obdidx" || error "$file1 missing EA"
7064         $LFS getstripe $fileN | grep -q "obdidx" || error "$fileN missing EA"
7065
7066         sleep 1  #make sure we get new statfs data
7067         df $dir
7068         local mdsfree2=$(do_facet $facet \
7069                          lctl get_param -n osd*.*$mdtname.kbytesfree)
7070         local mdcfree2=$(lctl get_param -n mdc.*$mdtname-mdc-*.kbytesfree)
7071
7072         if [[ $mdcfree2 -lt $((mdcfree - 16)) ]]; then
7073                 if [ "$mdsfree" != "$mdsfree2" ]; then
7074                         error "MDC before $mdcfree != after $mdcfree2"
7075                 else
7076                         echo "MDC before $mdcfree != after $mdcfree2"
7077                         echo "unable to confirm if MDS has large inodes"
7078                 fi
7079         fi
7080         rm -rf $dir
7081 }
7082 run_test 57b "default LOV EAs are stored inside large inodes ==="
7083
7084 test_58() {
7085         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7086         [ -z "$(which wiretest 2>/dev/null)" ] &&
7087                         skip_env "could not find wiretest"
7088
7089         wiretest
7090 }
7091 run_test 58 "verify cross-platform wire constants =============="
7092
7093 test_59() {
7094         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7095
7096         echo "touch 130 files"
7097         createmany -o $DIR/f59- 130
7098         echo "rm 130 files"
7099         unlinkmany $DIR/f59- 130
7100         sync
7101         # wait for commitment of removal
7102         wait_delete_completed
7103 }
7104 run_test 59 "verify cancellation of llog records async ========="
7105
7106 TEST60_HEAD="test_60 run $RANDOM"
7107 test_60a() {
7108         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7109         remote_mgs_nodsh && skip "remote MGS with nodsh"
7110         do_facet mgs "! which run-llog.sh &> /dev/null" &&
7111                 do_facet mgs "! ls run-llog.sh &> /dev/null" &&
7112                         skip_env "missing subtest run-llog.sh"
7113
7114         log "$TEST60_HEAD - from kernel mode"
7115         do_facet mgs "$LCTL dk > /dev/null"
7116         do_facet mgs "bash run-llog.sh" || error "run-llog.sh failed"
7117         do_facet mgs $LCTL dk > $TMP/$tfile
7118
7119         # LU-6388: test llog_reader
7120         local llog_reader=$(do_facet mgs "which llog_reader 2> /dev/null")
7121         llog_reader=${llog_reader:-$LUSTRE/utils/llog_reader}
7122         [ -z $(do_facet mgs ls -d $llog_reader 2> /dev/null) ] &&
7123                         skip_env "missing llog_reader"
7124         local fstype=$(facet_fstype mgs)
7125         [ $fstype != ldiskfs -a $fstype != zfs ] &&
7126                 skip_env "Only for ldiskfs or zfs type mgs"
7127
7128         local mntpt=$(facet_mntpt mgs)
7129         local mgsdev=$(mgsdevname 1)
7130         local fid_list
7131         local fid
7132         local rec_list
7133         local rec
7134         local rec_type
7135         local obj_file
7136         local path
7137         local seq
7138         local oid
7139         local pass=true
7140
7141         #get fid and record list
7142         fid_list=($(awk '/9_sub.*record/ { print $NF }' $TMP/$tfile |
7143                 tail -n 4))
7144         rec_list=($(awk '/9_sub.*record/ { print $((NF-3)) }' $TMP/$tfile |
7145                 tail -n 4))
7146         #remount mgs as ldiskfs or zfs type
7147         stop mgs || error "stop mgs failed"
7148         mount_fstype mgs || error "remount mgs failed"
7149         for ((i = 0; i < ${#fid_list[@]}; i++)); do
7150                 fid=${fid_list[i]}
7151                 rec=${rec_list[i]}
7152                 seq=$(echo $fid | awk -F ':' '{ print $1 }' | sed -e "s/^0x//g")
7153                 oid=$(echo $fid | awk -F ':' '{ print $2 }' | sed -e "s/^0x//g")
7154                 oid=$((16#$oid))
7155
7156                 case $fstype in
7157                         ldiskfs )
7158                                 obj_file=$mntpt/O/$seq/d$((oid%32))/$oid ;;
7159                         zfs )
7160                                 obj_file=$mntpt/oi.$(($((16#$seq))&127))/$fid ;;
7161                 esac
7162                 echo "obj_file is $obj_file"
7163                 do_facet mgs $llog_reader $obj_file
7164
7165                 rec_type=$(do_facet mgs $llog_reader $obj_file | grep "type=" |
7166                         awk '{ print $3 }' | sed -e "s/^type=//g")
7167                 if [ $rec_type != $rec ]; then
7168                         echo "FAILED test_60a wrong record type $rec_type," \
7169                               "should be $rec"
7170                         pass=false
7171                         break
7172                 fi
7173
7174                 #check obj path if record type is LLOG_LOGID_MAGIC
7175                 if [ "$rec" == "1064553b" ]; then
7176                         path=$(do_facet mgs $llog_reader $obj_file |
7177                                 grep "path=" | awk '{ print $NF }' |
7178                                 sed -e "s/^path=//g")
7179                         if [ $obj_file != $mntpt/$path ]; then
7180                                 echo "FAILED test_60a wrong obj path" \
7181                                       "$montpt/$path, should be $obj_file"
7182                                 pass=false
7183                                 break
7184                         fi
7185                 fi
7186         done
7187         rm -f $TMP/$tfile
7188         #restart mgs before "error", otherwise it will block the next test
7189         stop mgs || error "stop mgs failed"
7190         start mgs $(mgsdevname) $MGS_MOUNT_OPTS || error "start mgs failed"
7191         $pass || error "test failed, see FAILED test_60a messages for specifics"
7192 }
7193 run_test 60a "llog_test run from kernel module and test llog_reader"
7194
7195 test_60b() { # bug 6411
7196         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7197
7198         dmesg > $DIR/$tfile
7199         LLOG_COUNT=$(do_facet mgs dmesg |
7200                      awk "/$TEST60_HEAD/ { marker = 1; from_marker = 0; }
7201                           /llog_[a-z]*.c:[0-9]/ {
7202                                 if (marker)
7203                                         from_marker++
7204                                 from_begin++
7205                           }
7206                           END {
7207                                 if (marker)
7208                                         print from_marker
7209                                 else
7210                                         print from_begin
7211                           }")
7212
7213         [[ $LLOG_COUNT -gt 120 ]] &&
7214                 error "CDEBUG_LIMIT not limiting messages ($LLOG_COUNT)" || true
7215 }
7216 run_test 60b "limit repeated messages from CERROR/CWARN"
7217
7218 test_60c() {
7219         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7220
7221         echo "create 5000 files"
7222         createmany -o $DIR/f60c- 5000
7223 #define OBD_FAIL_MDS_LLOG_CREATE_FAILED  0x137
7224         lctl set_param fail_loc=0x80000137
7225         unlinkmany $DIR/f60c- 5000
7226         lctl set_param fail_loc=0
7227 }
7228 run_test 60c "unlink file when mds full"
7229
7230 test_60d() {
7231         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7232
7233         SAVEPRINTK=$(lctl get_param -n printk)
7234         # verify "lctl mark" is even working"
7235         MESSAGE="test message ID $RANDOM $$"
7236         $LCTL mark "$MESSAGE" || error "$LCTL mark failed"
7237         dmesg | grep -q "$MESSAGE" || error "didn't find debug marker in log"
7238
7239         lctl set_param printk=0 || error "set lnet.printk failed"
7240         lctl get_param -n printk | grep emerg || error "lnet.printk dropped emerg"
7241         MESSAGE="new test message ID $RANDOM $$"
7242         # Assume here that libcfs_debug_mark_buffer() uses D_WARNING
7243         $LCTL mark "$MESSAGE" || error "$LCTL mark failed"
7244         dmesg | grep -q "$MESSAGE" && error "D_WARNING wasn't masked" || true
7245
7246         lctl set_param -n printk="$SAVEPRINTK"
7247 }
7248 run_test 60d "test printk console message masking"
7249
7250 test_60e() {
7251         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7252         remote_mds_nodsh && skip "remote MDS with nodsh"
7253
7254         touch $DIR/$tfile
7255 #define OBD_FAIL_MDS_LLOG_CREATE_FAILED2  0x15b
7256         do_facet mds1 lctl set_param fail_loc=0x15b
7257         rm $DIR/$tfile
7258 }
7259 run_test 60e "no space while new llog is being created"
7260
7261 test_60g() {
7262         local pid
7263         local i
7264
7265         test_mkdir -c $MDSCOUNT $DIR/$tdir
7266
7267         (
7268                 local index=0
7269                 while true; do
7270                         $LFS setdirstripe -i $(($index % $MDSCOUNT)) \
7271                                 -c $MDSCOUNT $DIR/$tdir/subdir$index \
7272                                 2>/dev/null
7273                         mkdir $DIR/$tdir/subdir$index 2>/dev/null
7274                         rmdir $DIR/$tdir/subdir$index 2>/dev/null
7275                         index=$((index + 1))
7276                 done
7277         ) &
7278
7279         pid=$!
7280
7281         for i in {0..100}; do
7282                 # define OBD_FAIL_OSD_TXN_START    0x19a
7283                 local index=$((i % MDSCOUNT + 1))
7284
7285                 do_facet mds$index $LCTL set_param fail_loc=0x8000019a \
7286                         > /dev/null
7287                 usleep 100
7288         done
7289
7290         kill -9 $pid
7291
7292         for i in $(seq $MDSCOUNT); do
7293                 do_facet mds$i $LCTL set_param fail_loc=0 > /dev/null
7294         done
7295
7296         mkdir $DIR/$tdir/new || error "mkdir failed"
7297         rmdir $DIR/$tdir/new || error "rmdir failed"
7298
7299         do_facet mds1 $LCTL lfsck_start -M $(facet_svc mds1) -A -C \
7300                 -t namespace
7301         for i in $(seq $MDSCOUNT); do
7302                 wait_update_facet mds$i "$LCTL get_param -n \
7303                         mdd.$(facet_svc mds$i).lfsck_namespace |
7304                         awk '/^status/ { print \\\$2 }'" "completed"
7305         done
7306
7307         ls -R $DIR/$tdir || error "ls failed"
7308         rm -rf $DIR/$tdir || error "rmdir failed"
7309 }
7310 run_test 60g "transaction abort won't cause MDT hung"
7311
7312 test_60h() {
7313         [ $MDS1_VERSION -le $(version_code 2.12.52) ] &&
7314                 skip "Need MDS version at least 2.12.52"
7315         [ $MDSCOUNT -lt 2 ] && skip "Need at least 2 MDTs"
7316
7317         local f
7318
7319         #define OBD_FAIL_MDS_STRIPE_CREATE       0x188
7320         #define OBD_FAIL_MDS_STRIPE_FID          0x189
7321         for fail_loc in 0x80000188 0x80000189; do
7322                 do_facet mds1 "$LCTL set_param fail_loc=$fail_loc"
7323                 $LFS mkdir -c $MDSCOUNT -i 0 $DIR/$tdir-$fail_loc ||
7324                         error "mkdir $dir-$fail_loc failed"
7325                 for i in {0..10}; do
7326                         # create may fail on missing stripe
7327                         echo $i > $DIR/$tdir-$fail_loc/$i
7328                 done
7329                 $LFS getdirstripe $DIR/$tdir-$fail_loc ||
7330                         error "getdirstripe $tdir-$fail_loc failed"
7331                 $LFS migrate -m 1 $DIR/$tdir-$fail_loc ||
7332                         error "migrate $tdir-$fail_loc failed"
7333                 $LFS getdirstripe $DIR/$tdir-$fail_loc ||
7334                         error "getdirstripe $tdir-$fail_loc failed"
7335                 pushd $DIR/$tdir-$fail_loc
7336                 for f in *; do
7337                         echo $f | cmp $f - || error "$f data mismatch"
7338                 done
7339                 popd
7340                 rm -rf $DIR/$tdir-$fail_loc
7341         done
7342 }
7343 run_test 60h "striped directory with missing stripes can be accessed"
7344
7345 test_61a() {
7346         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7347
7348         f="$DIR/f61"
7349         dd if=/dev/zero of=$f bs=$PAGE_SIZE count=1 || error "dd $f failed"
7350         cancel_lru_locks osc
7351         $MULTIOP $f OSMWUc || error "$MULTIOP $f failed"
7352         sync
7353 }
7354 run_test 61a "mmap() writes don't make sync hang ================"
7355
7356 test_61b() {
7357         mmap_mknod_test $DIR/$tfile || error "mmap_mknod_test failed"
7358 }
7359 run_test 61b "mmap() of unstriped file is successful"
7360
7361 # bug 2330 - insufficient obd_match error checking causes LBUG
7362 test_62() {
7363         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7364
7365         f="$DIR/f62"
7366         echo foo > $f
7367         cancel_lru_locks osc
7368         lctl set_param fail_loc=0x405
7369         cat $f && error "cat succeeded, expect -EIO"
7370         lctl set_param fail_loc=0
7371 }
7372 # This test is now irrelevant (as of bug 10718 inclusion), we no longer
7373 # match every page all of the time.
7374 #run_test 62 "verify obd_match failure doesn't LBUG (should -EIO)"
7375
7376 # bug 2319 - oig_wait() interrupted causes crash because of invalid waitq.
7377 # Though this test is irrelevant anymore, it helped to reveal some
7378 # other grant bugs (LU-4482), let's keep it.
7379 test_63a() {   # was test_63
7380         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7381
7382         MAX_DIRTY_MB=$(lctl get_param -n osc.*.max_dirty_mb | head -n 1)
7383
7384         for i in `seq 10` ; do
7385                 dd if=/dev/zero of=$DIR/f63 bs=8k &
7386                 sleep 5
7387                 kill $!
7388                 sleep 1
7389         done
7390
7391         rm -f $DIR/f63 || true
7392 }
7393 run_test 63a "Verify oig_wait interruption does not crash ======="
7394
7395 # bug 2248 - async write errors didn't return to application on sync
7396 # bug 3677 - async write errors left page locked
7397 test_63b() {
7398         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7399
7400         debugsave
7401         lctl set_param debug=-1
7402
7403         # ensure we have a grant to do async writes
7404         dd if=/dev/zero of=$DIR/$tfile bs=4k count=1
7405         rm $DIR/$tfile
7406
7407         sync    # sync lest earlier test intercept the fail_loc
7408
7409         #define OBD_FAIL_OSC_BRW_PREP_REQ        0x406
7410         lctl set_param fail_loc=0x80000406
7411         $MULTIOP $DIR/$tfile Owy && \
7412                 error "sync didn't return ENOMEM"
7413         sync; sleep 2; sync     # do a real sync this time to flush page
7414         lctl get_param -n llite.*.dump_page_cache | grep locked && \
7415                 error "locked page left in cache after async error" || true
7416         debugrestore
7417 }
7418 run_test 63b "async write errors should be returned to fsync ==="
7419
7420 test_64a () {
7421         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7422
7423         df $DIR
7424         lctl get_param -n osc.*[oO][sS][cC][_-]*.cur* | grep "[0-9]"
7425 }
7426 run_test 64a "verify filter grant calculations (in kernel) ====="
7427
7428 test_64b () {
7429         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7430
7431         sh oos.sh $MOUNT || error "oos.sh failed: $?"
7432 }
7433 run_test 64b "check out-of-space detection on client"
7434
7435 test_64c() {
7436         $LCTL set_param osc.*OST0000-osc-[^mM]*.cur_grant_bytes=0
7437 }
7438 run_test 64c "verify grant shrink"
7439
7440 # this does exactly what osc_request.c:osc_announce_cached() does in
7441 # order to calculate max amount of grants to ask from server
7442 want_grant() {
7443         local tgt=$1
7444
7445         local nrpages=$($LCTL get_param -n osc.${tgt}.max_pages_per_rpc)
7446         local rpc_in_flight=$($LCTL get_param -n osc.${tgt}.max_rpcs_in_flight)
7447
7448         ((rpc_in_flight ++));
7449         nrpages=$((nrpages * rpc_in_flight))
7450
7451         local dirty_max_pages=$($LCTL get_param -n osc.${tgt}.max_dirty_mb)
7452
7453         dirty_max_pages=$((dirty_max_pages * 1024 * 1024 / PAGE_SIZE))
7454
7455         [[ $dirty_max_pages -gt $nrpages ]] && nrpages=$dirty_max_pages
7456         local undirty=$((nrpages * PAGE_SIZE))
7457
7458         local max_extent_pages
7459         max_extent_pages=$($LCTL get_param osc.${tgt}.import |
7460             grep grant_max_extent_size | awk '{print $2}')
7461         max_extent_pages=$((max_extent_pages / PAGE_SIZE))
7462         local nrextents=$(((nrpages + max_extent_pages - 1) / max_extent_pages))
7463         local grant_extent_tax
7464         grant_extent_tax=$($LCTL get_param osc.${tgt}.import |
7465             grep grant_extent_tax | awk '{print $2}')
7466
7467         undirty=$((undirty + nrextents * grant_extent_tax))
7468
7469         echo $undirty
7470 }
7471
7472 # this is size of unit for grant allocation. It should be equal to
7473 # what tgt_grant.c:tgt_grant_chunk() calculates
7474 grant_chunk() {
7475         local tgt=$1
7476         local max_brw_size
7477         local grant_extent_tax
7478
7479         max_brw_size=$($LCTL get_param osc.${tgt}.import |
7480             grep max_brw_size | awk '{print $2}')
7481
7482         grant_extent_tax=$($LCTL get_param osc.${tgt}.import |
7483             grep grant_extent_tax | awk '{print $2}')
7484
7485         echo $(((max_brw_size + grant_extent_tax) * 2))
7486 }
7487
7488 test_64d() {
7489         [ $OST1_VERSION -lt $(version_code 2.10.56) ] &&
7490                 skip "OST < 2.10.55 doesn't limit grants enough"
7491
7492         local tgt=$($LCTL dl | grep "0000-osc-[^mM]" | awk '{print $4}')
7493         local file=$DIR/$tfile
7494
7495         [[ $($LCTL get_param osc.${tgt}.import |
7496              grep "connect_flags:.*grant_param") ]] ||
7497                 skip "no grant_param connect flag"
7498
7499         local olddebug=$($LCTL get_param -n debug 2> /dev/null)
7500
7501         $LCTL set_param debug="$OLDDEBUG" 2> /dev/null || true
7502
7503         local max_cur_granted=$(($(want_grant $tgt) + $(grant_chunk $tgt)))
7504         stack_trap "rm -f $file" EXIT
7505
7506         $LFS setstripe $file -i 0 -c 1
7507         dd if=/dev/zero of=$file bs=1M count=1000 &
7508         ddpid=$!
7509
7510         while true
7511         do
7512                 local cur_grant=$($LCTL get_param -n osc.${tgt}.cur_grant_bytes)
7513                 if [[ $cur_grant -gt $max_cur_granted ]]
7514                 then
7515                         kill $ddpid
7516                         error "cur_grant $cur_grant > $max_cur_granted"
7517                 fi
7518                 kill -0 $ddpid
7519                 [[ $? -ne 0 ]] && break;
7520                 sleep 2
7521         done
7522
7523         rm -f $DIR/$tfile
7524         wait_delete_completed
7525         $LCTL set_param debug="$olddebug" 2> /dev/null || true
7526 }
7527 run_test 64d "check grant limit exceed"
7528
7529 # bug 1414 - set/get directories' stripe info
7530 test_65a() {
7531         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7532
7533         test_mkdir $DIR/$tdir
7534         touch $DIR/$tdir/f1
7535         $LVERIFY $DIR/$tdir $DIR/$tdir/f1 || error "lverify failed"
7536 }
7537 run_test 65a "directory with no stripe info"
7538
7539 test_65b() {
7540         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7541
7542         test_mkdir $DIR/$tdir
7543         local STRIPESIZE=$($LFS getstripe -S $DIR/$tdir)
7544
7545         $LFS setstripe -S $((STRIPESIZE * 2)) -i 0 -c 1 $DIR/$tdir ||
7546                                                 error "setstripe"
7547         touch $DIR/$tdir/f2
7548         $LVERIFY $DIR/$tdir $DIR/$tdir/f2 || error "lverify failed"
7549 }
7550 run_test 65b "directory setstripe -S stripe_size*2 -i 0 -c 1"
7551
7552 test_65c() {
7553         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7554         [ $OSTCOUNT -lt 2 ] && skip_env "need at least 2 OSTs"
7555
7556         test_mkdir $DIR/$tdir
7557         local stripesize=$($LFS getstripe -S $DIR/$tdir)
7558
7559         $LFS setstripe -S $((stripesize * 4)) -i 1 \
7560                 -c $((OSTCOUNT - 1)) $DIR/$tdir || error "setstripe"
7561         touch $DIR/$tdir/f3
7562         $LVERIFY $DIR/$tdir $DIR/$tdir/f3 || error "lverify failed"
7563 }
7564 run_test 65c "directory setstripe -S stripe_size*4 -i 1 -c $((OSTCOUNT-1))"
7565
7566 test_65d() {
7567         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7568
7569         test_mkdir $DIR/$tdir
7570         local STRIPECOUNT=$($LFS getstripe -c $DIR/$tdir)
7571         local STRIPESIZE=$($LFS getstripe -S $DIR/$tdir)
7572
7573         if [[ $STRIPECOUNT -le 0 ]]; then
7574                 sc=1
7575         elif [[ $STRIPECOUNT -gt $LOV_MAX_STRIPE_COUNT ]]; then
7576                 [[ $OSTCOUNT -gt $LOV_MAX_STRIPE_COUNT ]] &&
7577                         sc=$LOV_MAX_STRIPE_COUNT || sc=$(($OSTCOUNT - 1))
7578         else
7579                 sc=$(($STRIPECOUNT - 1))
7580         fi
7581         $LFS setstripe -S $STRIPESIZE -c $sc $DIR/$tdir || error "setstripe"
7582         touch $DIR/$tdir/f4 $DIR/$tdir/f5
7583         $LVERIFY $DIR/$tdir $DIR/$tdir/f4 $DIR/$tdir/f5 ||
7584                 error "lverify failed"
7585 }
7586 run_test 65d "directory setstripe -S stripe_size -c stripe_count"
7587
7588 test_65e() {
7589         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7590
7591         test_mkdir $DIR/$tdir
7592
7593         $LFS setstripe $DIR/$tdir || error "setstripe"
7594         $LFS getstripe -v $DIR/$tdir | grep "Default" ||
7595                                         error "no stripe info failed"
7596         touch $DIR/$tdir/f6
7597         $LVERIFY $DIR/$tdir $DIR/$tdir/f6 || error "lverify failed"
7598 }
7599 run_test 65e "directory setstripe defaults"
7600
7601 test_65f() {
7602         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7603
7604         test_mkdir $DIR/${tdir}f
7605         $RUNAS $LFS setstripe $DIR/${tdir}f &&
7606                 error "setstripe succeeded" || true
7607 }
7608 run_test 65f "dir setstripe permission (should return error) ==="
7609
7610 test_65g() {
7611         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7612
7613         test_mkdir $DIR/$tdir
7614         local STRIPESIZE=$($LFS getstripe -S $DIR/$tdir)
7615
7616         $LFS setstripe -S $((STRIPESIZE * 2)) -i 0 -c 1 $DIR/$tdir ||
7617                 error "setstripe -S failed"
7618         $LFS setstripe -d $DIR/$tdir || error "setstripe -d failed"
7619         $LFS getstripe -v $DIR/$tdir | grep "Default" ||
7620                 error "delete default stripe failed"
7621 }
7622 run_test 65g "directory setstripe -d"
7623
7624 test_65h() {
7625         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7626
7627         test_mkdir $DIR/$tdir
7628         local STRIPESIZE=$($LFS getstripe -S $DIR/$tdir)
7629
7630         $LFS setstripe -S $((STRIPESIZE * 2)) -i 0 -c 1 $DIR/$tdir ||
7631                 error "setstripe -S failed"
7632         test_mkdir $DIR/$tdir/dd1
7633         [ $($LFS getstripe -c $DIR/$tdir) = $($LFS getstripe -c $DIR/$tdir/dd1) ] ||
7634                 error "stripe info inherit failed"
7635 }
7636 run_test 65h "directory stripe info inherit ===================="
7637
7638 test_65i() {
7639         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7640
7641         save_layout_restore_at_exit $MOUNT
7642
7643         # bug6367: set non-default striping on root directory
7644         $LFS setstripe -S 65536 -c -1 $MOUNT || error "error setting stripe"
7645
7646         # bug12836: getstripe on -1 default directory striping
7647         $LFS getstripe $MOUNT || error "getstripe $MOUNT failed"
7648
7649         # bug12836: getstripe -v on -1 default directory striping
7650         $LFS getstripe -v $MOUNT || error "getstripe -v $MOUNT failed"
7651
7652         # bug12836: new find on -1 default directory striping
7653         $LFS find -mtime -1 $MOUNT > /dev/null || error "find $MOUNT failed"
7654 }
7655 run_test 65i "various tests to set root directory striping"
7656
7657 test_65j() { # bug6367
7658         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7659
7660         sync; sleep 1
7661
7662         # if we aren't already remounting for each test, do so for this test
7663         if [ "$I_MOUNTED" = "yes" ]; then
7664                 cleanup || error "failed to unmount"
7665                 setup
7666         fi
7667
7668         save_layout_restore_at_exit $MOUNT
7669
7670         $LFS setstripe -d $MOUNT || error "setstripe failed"
7671 }
7672 run_test 65j "set default striping on root directory (bug 6367)="
7673
7674 cleanup_65k() {
7675         rm -rf $DIR/$tdir
7676         wait_delete_completed
7677         do_facet $SINGLEMDS "lctl set_param -n \
7678                 osp.$ost*MDT0000.max_create_count=$max_count"
7679         do_facet $SINGLEMDS "lctl set_param -n \
7680                 osp.$ost*MDT0000.create_count=$count"
7681         do_facet $SINGLEMDS lctl --device  %$INACTIVE_OSC activate
7682         echo $INACTIVE_OSC "is Activate"
7683
7684         wait_osc_import_state mds ost$(( ostnum + 1 )) FULL
7685 }
7686
7687 test_65k() { # bug11679
7688         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7689         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
7690         remote_mds_nodsh && skip "remote MDS with nodsh"
7691
7692         local disable_precreate=true
7693         [ $MDS1_VERSION -le $(version_code 2.8.54) ] &&
7694                 disable_precreate=false
7695
7696         echo "Check OST status: "
7697         local MDS_OSCS=$(do_facet $SINGLEMDS lctl dl |
7698                 awk '/[oO][sS][cC].*md[ts]/ { print $4 }')
7699
7700         for OSC in $MDS_OSCS; do
7701                 echo $OSC "is active"
7702                 do_facet $SINGLEMDS lctl --device %$OSC activate
7703         done
7704
7705         for INACTIVE_OSC in $MDS_OSCS; do
7706                 local ost=$(osc_to_ost $INACTIVE_OSC)
7707                 local ostnum=$(do_facet $SINGLEMDS lctl get_param -n \
7708                                lov.*md*.target_obd |
7709                                awk -F: /$ost/'{ print $1 }' | head -n 1)
7710
7711                 mkdir -p $DIR/$tdir
7712                 $LFS setstripe -i $ostnum -c 1 $DIR/$tdir
7713                 createmany -o $DIR/$tdir/$tfile.$ostnum. 1000
7714
7715                 echo "Deactivate: " $INACTIVE_OSC
7716                 do_facet $SINGLEMDS lctl --device %$INACTIVE_OSC deactivate
7717
7718                 local count=$(do_facet $SINGLEMDS "lctl get_param -n \
7719                               osp.$ost*MDT0000.create_count")
7720                 local max_count=$(do_facet $SINGLEMDS "lctl get_param -n \
7721                                   osp.$ost*MDT0000.max_create_count")
7722                 $disable_precreate &&
7723                         do_facet $SINGLEMDS "lctl set_param -n \
7724                                 osp.$ost*MDT0000.max_create_count=0"
7725
7726                 for idx in $(seq 0 $((OSTCOUNT - 1))); do
7727                         [ -f $DIR/$tdir/$idx ] && continue
7728                         echo "$LFS setstripe -i $idx -c 1 $DIR/$tdir/$idx"
7729                         $LFS setstripe -i $idx -c 1 $DIR/$tdir/$idx ||
7730                                 { cleanup_65k;
7731                                   error "setstripe $idx should succeed"; }
7732                         rm -f $DIR/$tdir/$idx || error "rm $idx failed"
7733                 done
7734                 unlinkmany $DIR/$tdir/$tfile.$ostnum. 1000
7735                 rmdir $DIR/$tdir
7736
7737                 do_facet $SINGLEMDS "lctl set_param -n \
7738                         osp.$ost*MDT0000.max_create_count=$max_count"
7739                 do_facet $SINGLEMDS "lctl set_param -n \
7740                         osp.$ost*MDT0000.create_count=$count"
7741                 do_facet $SINGLEMDS lctl --device  %$INACTIVE_OSC activate
7742                 echo $INACTIVE_OSC "is Activate"
7743
7744                 wait_osc_import_state mds ost$(( ostnum + 1 )) FULL
7745         done
7746 }
7747 run_test 65k "validate manual striping works properly with deactivated OSCs"
7748
7749 test_65l() { # bug 12836
7750         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7751
7752         test_mkdir -p $DIR/$tdir/test_dir
7753         $LFS setstripe -c -1 $DIR/$tdir/test_dir
7754         $LFS find -mtime -1 $DIR/$tdir >/dev/null
7755 }
7756 run_test 65l "lfs find on -1 stripe dir ========================"
7757
7758 test_65m() {
7759         local layout=$(save_layout $MOUNT)
7760         $RUNAS $LFS setstripe -c 2 $MOUNT && {
7761                 restore_layout $MOUNT $layout
7762                 error "setstripe should fail by non-root users"
7763         }
7764         true
7765 }
7766 run_test 65m "normal user can't set filesystem default stripe"
7767
7768 test_65n() {
7769         [ -n "$FILESET" ] && skip "Not functional for FILESET set"
7770         [[ $(lustre_version_code $SINGLEMDS) -ge $(version_code 2.12.50) ]] ||
7771                 skip "Need MDS version at least 2.12.50"
7772         [[ $PARALLEL != "yes" ]] || skip "skip parallel run"
7773
7774         [[ $OSTCOUNT -ge 2 ]] || skip_env "needs >= 2 OSTs"
7775         which getfattr > /dev/null 2>&1 || skip_env "no getfattr command"
7776         which setfattr > /dev/null 2>&1 || skip_env "no setfattr command"
7777
7778         local root_layout=$(save_layout $MOUNT)
7779         stack_trap "restore_layout $MOUNT $root_layout" EXIT
7780
7781         # new subdirectory under root directory should not inherit
7782         # the default layout from root
7783         local dir1=$MOUNT/$tdir-1
7784         mkdir $dir1 || error "mkdir $dir1 failed"
7785         ! getfattr -n trusted.lov $dir1 &> /dev/null ||
7786                 error "$dir1 shouldn't have LOV EA"
7787
7788         # delete the default layout on root directory
7789         $LFS setstripe -d $MOUNT || error "delete root default layout failed"
7790
7791         local dir2=$MOUNT/$tdir-2
7792         mkdir $dir2 || error "mkdir $dir2 failed"
7793         ! getfattr -n trusted.lov $dir2 &> /dev/null ||
7794                 error "$dir2 shouldn't have LOV EA"
7795
7796         # set a new striping pattern on root directory
7797         local def_stripe_size=$($LFS getstripe -S $MOUNT)
7798         local new_def_stripe_size=$((def_stripe_size * 2))
7799         $LFS setstripe -S $new_def_stripe_size $MOUNT ||
7800                 error "set stripe size on $MOUNT failed"
7801
7802         # new file created in $dir2 should inherit the new stripe size from
7803         # the filesystem default
7804         local file2=$dir2/$tfile-2
7805         touch $file2 || error "touch $file2 failed"
7806
7807         local file2_stripe_size=$($LFS getstripe -S $file2)
7808         [[ $file2_stripe_size -eq $new_def_stripe_size ]] ||
7809                 error "$file2 didn't inherit stripe size $new_def_stripe_size"
7810
7811         local dir3=$MOUNT/$tdir-3
7812         mkdir $dir3 || error "mkdir $dir3 failed"
7813         ! getfattr -n trusted.lov $dir3 &> /dev/null ||
7814                 error "$dir3 shouldn't have LOV EA"
7815
7816         # set OST pool on root directory
7817         local pool=$TESTNAME
7818         pool_add $pool || error "add $pool failed"
7819         pool_add_targets $pool 0 $((OSTCOUNT - 1)) 1 ||
7820                 error "add targets to $pool failed"
7821
7822         $LFS setstripe -p $pool $MOUNT ||
7823                 error "set OST pool on $MOUNT failed"
7824
7825         # new file created in $dir3 should inherit the pool from
7826         # the filesystem default
7827         local file3=$dir3/$tfile-3
7828         touch $file3 || error "touch $file3 failed"
7829
7830         local file3_pool=$($LFS getstripe -p $file3)
7831         [[ "$file3_pool" = "$pool" ]] ||
7832                 error "$file3 didn't inherit OST pool $pool"
7833
7834         local dir4=$MOUNT/$tdir-4
7835         mkdir $dir4 || error "mkdir $dir4 failed"
7836         ! getfattr -n trusted.lov $dir4 &> /dev/null ||
7837                 error "$dir4 shouldn't have LOV EA"
7838
7839         # new file created in $dir4 should inherit the pool from
7840         # the filesystem default
7841         local file4=$dir4/$tfile-4
7842         touch $file4 || error "touch $file4 failed"
7843
7844         local file4_pool=$($LFS getstripe -p $file4)
7845         [[ "$file4_pool" = "$pool" ]] ||
7846                 error "$file4 didn't inherit OST pool $pool"
7847
7848         # new subdirectory under non-root directory should inherit
7849         # the default layout from its parent directory
7850         $LFS setstripe -S $new_def_stripe_size -p $pool $dir4 ||
7851                 error "set directory layout on $dir4 failed"
7852
7853         local dir5=$dir4/$tdir-5
7854         mkdir $dir5 || error "mkdir $dir5 failed"
7855
7856         local dir4_layout=$(get_layout_param $dir4)
7857         local dir5_layout=$(get_layout_param $dir5)
7858         [[ "$dir4_layout" = "$dir5_layout" ]] ||
7859                 error "$dir5 should inherit the default layout from $dir4"
7860
7861         # though subdir under ROOT doesn't inherit default layout, but
7862         # its sub dir/file should be created with default layout.
7863         [[ $MDSCOUNT -ge 2 ]] || skip_env "needs >= 2 MDTs"
7864         [[ $MDS1_VERSION -ge $(version_code 2.12.59) ]] ||
7865                 skip "Need MDS version at least 2.12.59"
7866
7867         local default_lmv_count=$($LFS getdirstripe -D -c $MOUNT)
7868         local default_lmv_index=$($LFS getdirstripe -D -i $MOUNT)
7869         local default_lmv_hash=$($LFS getdirstripe -D -H $MOUNT)
7870
7871         if [ $default_lmv_hash == "none" ]; then
7872                 stack_trap "$LFS setdirstripe -D -d $MOUNT" EXIT
7873         else
7874                 stack_trap "$LFS setdirstripe -D -i $default_lmv_index \
7875                         -c $default_lmv_count -H $default_lmv_hash $MOUNT" EXIT
7876         fi
7877
7878         $LFS setdirstripe -D -c 2 $MOUNT ||
7879                 error "setdirstripe -D -c 2 failed"
7880         mkdir $MOUNT/$tdir-6 || error "mkdir $tdir-6 failed"
7881         local lmv_count=$($LFS getdirstripe -c $MOUNT/$tdir-6)
7882         [ $lmv_count -eq 2 ] || error "$tdir-6 stripe count $lmv_count"
7883 }
7884 run_test 65n "don't inherit default layout from root for new subdirectories"
7885
7886 # bug 2543 - update blocks count on client
7887 test_66() {
7888         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7889
7890         COUNT=${COUNT:-8}
7891         dd if=/dev/zero of=$DIR/f66 bs=1k count=$COUNT
7892         sync; sync_all_data; sync; sync_all_data
7893         cancel_lru_locks osc
7894         BLOCKS=`ls -s $DIR/f66 | awk '{ print $1 }'`
7895         [ $BLOCKS -ge $COUNT ] || error "$DIR/f66 blocks $BLOCKS < $COUNT"
7896 }
7897 run_test 66 "update inode blocks count on client ==============="
7898
7899 meminfo() {
7900         awk '($1 == "'$1':") { print $2 }' /proc/meminfo
7901 }
7902
7903 swap_used() {
7904         swapon -s | awk '($1 == "'$1'") { print $4 }'
7905 }
7906
7907 # bug5265, obdfilter oa2dentry return -ENOENT
7908 # #define OBD_FAIL_SRV_ENOENT 0x217
7909 test_69() {
7910         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7911         remote_ost_nodsh && skip "remote OST with nodsh"
7912
7913         f="$DIR/$tfile"
7914         $LFS setstripe -c 1 -i 0 $f
7915
7916         $DIRECTIO write ${f}.2 0 1 || error "directio write error"
7917
7918         do_facet ost1 lctl set_param fail_loc=0x217
7919         $TRUNCATE $f 1 # vmtruncate() will ignore truncate() error.
7920         $DIRECTIO write $f 0 2 && error "write succeeded, expect -ENOENT"
7921
7922         do_facet ost1 lctl set_param fail_loc=0
7923         $DIRECTIO write $f 0 2 || error "write error"
7924
7925         cancel_lru_locks osc
7926         $DIRECTIO read $f 0 1 || error "read error"
7927
7928         do_facet ost1 lctl set_param fail_loc=0x217
7929         $DIRECTIO read $f 1 1 && error "read succeeded, expect -ENOENT"
7930
7931         do_facet ost1 lctl set_param fail_loc=0
7932         rm -f $f
7933 }
7934 run_test 69 "verify oa2dentry return -ENOENT doesn't LBUG ======"
7935
7936 test_71() {
7937         test_mkdir $DIR/$tdir
7938         $LFS setdirstripe -D -c$MDSCOUNT $DIR/$tdir
7939         sh rundbench -C -D $DIR/$tdir 2 || error "dbench failed!"
7940 }
7941 run_test 71 "Running dbench on lustre (don't segment fault) ===="
7942
7943 test_72a() { # bug 5695 - Test that on 2.6 remove_suid works properly
7944         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7945         [ "$RUNAS_ID" = "$UID" ] &&
7946                 skip_env "RUNAS_ID = UID = $UID -- skipping"
7947         # Check that testing environment is properly set up. Skip if not
7948         FAIL_ON_ERROR=false check_runas_id_ret $RUNAS_ID $RUNAS_GID $RUNAS ||
7949                 skip_env "User $RUNAS_ID does not exist - skipping"
7950
7951         touch $DIR/$tfile
7952         chmod 777 $DIR/$tfile
7953         chmod ug+s $DIR/$tfile
7954         $RUNAS dd if=/dev/zero of=$DIR/$tfile bs=512 count=1 ||
7955                 error "$RUNAS dd $DIR/$tfile failed"
7956         # See if we are still setuid/sgid
7957         [ -u $DIR/$tfile ] || [ -g $DIR/$tfile ] &&
7958                 error "S/gid is not dropped on write"
7959         # Now test that MDS is updated too
7960         cancel_lru_locks mdc
7961         [ -u $DIR/$tfile ] || [ -g $DIR/$tfile ] &&
7962                 error "S/gid is not dropped on MDS"
7963         rm -f $DIR/$tfile
7964 }
7965 run_test 72a "Test that remove suid works properly (bug5695) ===="
7966
7967 test_72b() { # bug 24226 -- keep mode setting when size is not changing
7968         local perm
7969
7970         [ "$RUNAS_ID" = "$UID" ] &&
7971                 skip_env "RUNAS_ID = UID = $UID -- skipping"
7972         [ "$RUNAS_ID" -eq 0 ] &&
7973                 skip_env "RUNAS_ID = 0 -- skipping"
7974         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7975         # Check that testing environment is properly set up. Skip if not
7976         FAIL_ON_ERROR=false check_runas_id_ret $RUNAS_ID $RUNAS_ID $RUNAS ||
7977                 skip_env "User $RUNAS_ID does not exist - skipping"
7978
7979         touch $DIR/${tfile}-f{g,u}
7980         test_mkdir $DIR/${tfile}-dg
7981         test_mkdir $DIR/${tfile}-du
7982         chmod 770 $DIR/${tfile}-{f,d}{g,u}
7983         chmod g+s $DIR/${tfile}-{f,d}g
7984         chmod u+s $DIR/${tfile}-{f,d}u
7985         for perm in 777 2777 4777; do
7986                 $RUNAS chmod $perm $DIR/${tfile}-fg && error "S/gid file allowed improper chmod to $perm"
7987                 $RUNAS chmod $perm $DIR/${tfile}-fu && error "S/uid file allowed improper chmod to $perm"
7988                 $RUNAS chmod $perm $DIR/${tfile}-dg && error "S/gid dir allowed improper chmod to $perm"
7989                 $RUNAS chmod $perm $DIR/${tfile}-du && error "S/uid dir allowed improper chmod to $perm"
7990         done
7991         true
7992 }
7993 run_test 72b "Test that we keep mode setting if without file data changed (bug 24226)"
7994
7995 # bug 3462 - multiple simultaneous MDC requests
7996 test_73() {
7997         [ $PARALLEL == "yes" ] && skip "skip parallel run"
7998
7999         test_mkdir $DIR/d73-1
8000         test_mkdir $DIR/d73-2
8001         multiop_bg_pause $DIR/d73-1/f73-1 O_c || return 1
8002         pid1=$!
8003
8004         lctl set_param fail_loc=0x80000129
8005         $MULTIOP $DIR/d73-1/f73-2 Oc &
8006         sleep 1
8007         lctl set_param fail_loc=0
8008
8009         $MULTIOP $DIR/d73-2/f73-3 Oc &
8010         pid3=$!
8011
8012         kill -USR1 $pid1
8013         wait $pid1 || return 1
8014
8015         sleep 25
8016
8017         $CHECKSTAT -t file $DIR/d73-1/f73-1 || return 4
8018         $CHECKSTAT -t file $DIR/d73-1/f73-2 || return 5
8019         $CHECKSTAT -t file $DIR/d73-2/f73-3 || return 6
8020
8021         rm -rf $DIR/d73-*
8022 }
8023 run_test 73 "multiple MDC requests (should not deadlock)"
8024
8025 test_74a() { # bug 6149, 6184
8026         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8027
8028         touch $DIR/f74a
8029         #define OBD_FAIL_LDLM_ENQUEUE_OLD_EXPORT 0x30e
8030         #
8031         # very important to OR with OBD_FAIL_ONCE (0x80000000) -- otherwise it
8032         # will spin in a tight reconnection loop
8033         $LCTL set_param fail_loc=0x8000030e
8034         # get any lock that won't be difficult - lookup works.
8035         ls $DIR/f74a
8036         $LCTL set_param fail_loc=0
8037         rm -f $DIR/f74a
8038         true
8039 }
8040 run_test 74a "ldlm_enqueue freed-export error path, ls (shouldn't LBUG)"
8041
8042 test_74b() { # bug 13310
8043         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8044
8045         #define OBD_FAIL_LDLM_ENQUEUE_OLD_EXPORT 0x30e
8046         #
8047         # very important to OR with OBD_FAIL_ONCE (0x80000000) -- otherwise it
8048         # will spin in a tight reconnection loop
8049         $LCTL set_param fail_loc=0x8000030e
8050         # get a "difficult" lock
8051         touch $DIR/f74b
8052         $LCTL set_param fail_loc=0
8053         rm -f $DIR/f74b
8054         true
8055 }
8056 run_test 74b "ldlm_enqueue freed-export error path, touch (shouldn't LBUG)"
8057
8058 test_74c() {
8059         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8060
8061         #define OBD_FAIL_LDLM_NEW_LOCK
8062         $LCTL set_param fail_loc=0x319
8063         touch $DIR/$tfile && error "touch successful"
8064         $LCTL set_param fail_loc=0
8065         true
8066 }
8067 run_test 74c "ldlm_lock_create error path, (shouldn't LBUG)"
8068
8069 num_inodes() {
8070         awk '/lustre_inode_cache/ {print $2; exit}' /proc/slabinfo
8071 }
8072
8073 test_76() { # Now for bug 20433, added originally in bug 1443
8074         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8075
8076         local CPUS=$(getconf _NPROCESSORS_ONLN 2>/dev/null)
8077
8078         cancel_lru_locks osc
8079         BEFORE_INODES=$(num_inodes)
8080         echo "before inodes: $BEFORE_INODES"
8081         local COUNT=1000
8082         [ "$SLOW" = "no" ] && COUNT=100
8083         for i in $(seq $COUNT); do
8084                 touch $DIR/$tfile
8085                 rm -f $DIR/$tfile
8086         done
8087         cancel_lru_locks osc
8088         AFTER_INODES=$(num_inodes)
8089         echo "after inodes: $AFTER_INODES"
8090         local wait=0
8091         while [[ $((AFTER_INODES-1*${CPUS:-1})) -gt $BEFORE_INODES ]]; do
8092                 sleep 2
8093                 AFTER_INODES=$(num_inodes)
8094                 wait=$((wait+2))
8095                 echo "wait $wait seconds inodes: $AFTER_INODES"
8096                 if [ $wait -gt 30 ]; then
8097                         error "inode slab grew from $BEFORE_INODES to $AFTER_INODES"
8098                 fi
8099         done
8100 }
8101 run_test 76 "confirm clients recycle inodes properly ===="
8102
8103
8104 export ORIG_CSUM=""
8105 set_checksums()
8106 {
8107         # Note: in sptlrpc modes which enable its own bulk checksum, the
8108         # original crc32_le bulk checksum will be automatically disabled,
8109         # and the OBD_FAIL_OSC_CHECKSUM_SEND/OBD_FAIL_OSC_CHECKSUM_RECEIVE
8110         # will be checked by sptlrpc code against sptlrpc bulk checksum.
8111         # In this case set_checksums() will not be no-op, because sptlrpc
8112         # bulk checksum will be enabled all through the test.
8113
8114         [ "$ORIG_CSUM" ] || ORIG_CSUM=`lctl get_param -n osc.*.checksums | head -n1`
8115         lctl set_param -n osc.*.checksums $1
8116         return 0
8117 }
8118
8119 export ORIG_CSUM_TYPE="`lctl get_param -n osc.*osc-[^mM]*.checksum_type |
8120                         sed 's/.*\[\(.*\)\].*/\1/g' | head -n1`"
8121 CKSUM_TYPES=${CKSUM_TYPES:-$(lctl get_param -n osc.*osc-[^mM]*.checksum_type |
8122                              tr -d [] | head -n1)}
8123 set_checksum_type()
8124 {
8125         lctl set_param -n osc.*osc-[^mM]*.checksum_type $1
8126         rc=$?
8127         log "set checksum type to $1, rc = $rc"
8128         return $rc
8129 }
8130
8131 get_osc_checksum_type()
8132 {
8133         # arugment 1: OST name, like OST0000
8134         ost=$1
8135         checksum_type=$(lctl get_param -n osc.*${ost}-osc-[^mM]*.checksum_type |
8136                         sed 's/.*\[\(.*\)\].*/\1/g')
8137         rc=$?
8138         [ $rc -ne 0 ] && error "failed to get checksum type of $ost, rc = $rc, output = $checksum_type"
8139         echo $checksum_type
8140 }
8141
8142 F77_TMP=$TMP/f77-temp
8143 F77SZ=8
8144 setup_f77() {
8145         dd if=/dev/urandom of=$F77_TMP bs=1M count=$F77SZ || \
8146                 error "error writing to $F77_TMP"
8147 }
8148
8149 test_77a() { # bug 10889
8150         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8151         $GSS && skip_env "could not run with gss"
8152
8153         [ ! -f $F77_TMP ] && setup_f77
8154         set_checksums 1
8155         dd if=$F77_TMP of=$DIR/$tfile bs=1M count=$F77SZ || error "dd error"
8156         set_checksums 0
8157         rm -f $DIR/$tfile
8158 }
8159 run_test 77a "normal checksum read/write operation"
8160
8161 test_77b() { # bug 10889
8162         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8163         $GSS && skip_env "could not run with gss"
8164
8165         [ ! -f $F77_TMP ] && setup_f77
8166         #define OBD_FAIL_OSC_CHECKSUM_SEND       0x409
8167         $LCTL set_param fail_loc=0x80000409
8168         set_checksums 1
8169
8170         dd if=$F77_TMP of=$DIR/$tfile bs=1M count=$F77SZ conv=sync ||
8171                 error "dd error: $?"
8172         $LCTL set_param fail_loc=0
8173
8174         for algo in $CKSUM_TYPES; do
8175                 cancel_lru_locks osc
8176                 set_checksum_type $algo
8177                 #define OBD_FAIL_OSC_CHECKSUM_RECEIVE    0x408
8178                 $LCTL set_param fail_loc=0x80000408
8179                 cmp $F77_TMP $DIR/$tfile || error "file compare failed"
8180                 $LCTL set_param fail_loc=0
8181         done
8182         set_checksums 0
8183         set_checksum_type $ORIG_CSUM_TYPE
8184         rm -f $DIR/$tfile
8185 }
8186 run_test 77b "checksum error on client write, read"
8187
8188 cleanup_77c() {
8189         trap 0
8190         set_checksums 0
8191         $LCTL set_param osc.*osc-[^mM]*.checksum_dump=0
8192         $check_ost &&
8193                 do_facet ost1 $LCTL set_param obdfilter.*-OST*.checksum_dump=0
8194         [ -n "$osc_file_prefix" ] && rm -f ${osc_file_prefix}*
8195         $check_ost && [ -n "$ost_file_prefix" ] &&
8196                 do_facet ost1 rm -f ${ost_file_prefix}\*
8197 }
8198
8199 test_77c() {
8200         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8201         $GSS && skip_env "could not run with gss"
8202         remote_ost_nodsh && skip "remote OST with nodsh"
8203
8204         local bad1
8205         local osc_file_prefix
8206         local osc_file
8207         local check_ost=false
8208         local ost_file_prefix
8209         local ost_file
8210         local orig_cksum
8211         local dump_cksum
8212         local fid
8213
8214         # ensure corruption will occur on first OSS/OST
8215         $LFS setstripe -i 0 $DIR/$tfile
8216
8217         [ ! -f $F77_TMP ] && setup_f77
8218         dd if=$F77_TMP of=$DIR/$tfile bs=1M count=$F77SZ conv=sync ||
8219                 error "dd write error: $?"
8220         fid=$($LFS path2fid $DIR/$tfile)
8221
8222         if [ $OST1_VERSION -ge $(version_code 2.9.57) ]
8223         then
8224                 check_ost=true
8225                 ost_file_prefix=$(do_facet ost1 $LCTL get_param -n debug_path)
8226                 ost_file_prefix=${ost_file_prefix}-checksum_dump-ost-\\${fid}
8227         else
8228                 echo "OSS do not support bulk pages dump upon error"
8229         fi
8230
8231         osc_file_prefix=$($LCTL get_param -n debug_path)
8232         osc_file_prefix=${osc_file_prefix}-checksum_dump-osc-\\${fid}
8233
8234         trap cleanup_77c EXIT
8235
8236         set_checksums 1
8237         # enable bulk pages dump upon error on Client
8238         $LCTL set_param osc.*osc-[^mM]*.checksum_dump=1
8239         # enable bulk pages dump upon error on OSS
8240         $check_ost &&
8241                 do_facet ost1 $LCTL set_param obdfilter.*-OST*.checksum_dump=1
8242
8243         # flush Client cache to allow next read to reach OSS
8244         cancel_lru_locks osc
8245
8246         #define OBD_FAIL_OSC_CHECKSUM_RECEIVE       0x408
8247         $LCTL set_param fail_loc=0x80000408
8248         dd if=$DIR/$tfile of=/dev/null bs=1M || error "dd read error: $?"
8249         $LCTL set_param fail_loc=0
8250
8251         rm -f $DIR/$tfile
8252
8253         # check cksum dump on Client
8254         osc_file=$(ls ${osc_file_prefix}*)
8255         [ -n "$osc_file" ] || error "no checksum dump file on Client"
8256         # OBD_FAIL_OSC_CHECKSUM_RECEIVE corrupts with "bad1" at start of file
8257         bad1=$(dd if=$osc_file bs=1 count=4 2>/dev/null) || error "dd error: $?"
8258         [ $bad1 == "bad1" ] || error "unexpected corrupt pattern"
8259         orig_cksum=$(dd if=$F77_TMP bs=1 skip=4 count=1048572 2>/dev/null |
8260                      cksum)
8261         dump_cksum=$(dd if=$osc_file bs=1 skip=4 2>/dev/null | cksum)
8262         [[ "$orig_cksum" == "$dump_cksum" ]] ||
8263                 error "dump content does not match on Client"
8264
8265         $check_ost || skip "No need to check cksum dump on OSS"
8266
8267         # check cksum dump on OSS
8268         ost_file=$(do_facet ost1 ls ${ost_file_prefix}\*)
8269         [ -n "$ost_file" ] || error "no checksum dump file on OSS"
8270         orig_cksum=$(dd if=$F77_TMP bs=1048576 count=1 2>/dev/null | cksum)
8271         dump_cksum=$(do_facet ost1 dd if=$ost_file 2>/dev/null \| cksum)
8272         [[ "$orig_cksum" == "$dump_cksum" ]] ||
8273                 error "dump content does not match on OSS"
8274
8275         cleanup_77c
8276 }
8277 run_test 77c "checksum error on client read with debug"
8278
8279 test_77d() { # bug 10889
8280         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8281         $GSS && skip_env "could not run with gss"
8282
8283         #define OBD_FAIL_OSC_CHECKSUM_SEND       0x409
8284         $LCTL set_param fail_loc=0x80000409
8285         set_checksums 1
8286         $DIRECTIO write $DIR/$tfile 0 $F77SZ $((1024 * 1024)) ||
8287                 error "direct write: rc=$?"
8288         $LCTL set_param fail_loc=0
8289         set_checksums 0
8290
8291         #define OBD_FAIL_OSC_CHECKSUM_RECEIVE    0x408
8292         $LCTL set_param fail_loc=0x80000408
8293         set_checksums 1
8294         cancel_lru_locks osc
8295         $DIRECTIO read $DIR/$tfile 0 $F77SZ $((1024 * 1024)) ||
8296                 error "direct read: rc=$?"
8297         $LCTL set_param fail_loc=0
8298         set_checksums 0
8299 }
8300 run_test 77d "checksum error on OST direct write, read"
8301
8302 test_77f() { # bug 10889
8303         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8304         $GSS && skip_env "could not run with gss"
8305
8306         set_checksums 1
8307         for algo in $CKSUM_TYPES; do
8308                 cancel_lru_locks osc
8309                 set_checksum_type $algo
8310                 #define OBD_FAIL_OSC_CHECKSUM_SEND       0x409
8311                 $LCTL set_param fail_loc=0x409
8312                 $DIRECTIO write $DIR/$tfile 0 $F77SZ $((1024 * 1024)) &&
8313                         error "direct write succeeded"
8314                 $LCTL set_param fail_loc=0
8315         done
8316         set_checksum_type $ORIG_CSUM_TYPE
8317         set_checksums 0
8318 }
8319 run_test 77f "repeat checksum error on write (expect error)"
8320
8321 test_77g() { # bug 10889
8322         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8323         $GSS && skip_env "could not run with gss"
8324         remote_ost_nodsh && skip "remote OST with nodsh"
8325
8326         [ ! -f $F77_TMP ] && setup_f77
8327
8328         local file=$DIR/$tfile
8329         stack_trap "rm -f $file" EXIT
8330
8331         $LFS setstripe -c 1 -i 0 $file
8332         #define OBD_FAIL_OST_CHECKSUM_RECEIVE       0x21a
8333         do_facet ost1 lctl set_param fail_loc=0x8000021a
8334         set_checksums 1
8335         dd if=$F77_TMP of=$file bs=1M count=$F77SZ ||
8336                 error "write error: rc=$?"
8337         do_facet ost1 lctl set_param fail_loc=0
8338         set_checksums 0
8339
8340         cancel_lru_locks osc
8341         #define OBD_FAIL_OST_CHECKSUM_SEND          0x21b
8342         do_facet ost1 lctl set_param fail_loc=0x8000021b
8343         set_checksums 1
8344         cmp $F77_TMP $file || error "file compare failed"
8345         do_facet ost1 lctl set_param fail_loc=0
8346         set_checksums 0
8347 }
8348 run_test 77g "checksum error on OST write, read"
8349
8350 test_77k() { # LU-10906
8351         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8352         $GSS && skip_env "could not run with gss"
8353
8354         local cksum_param="osc.$FSNAME*.checksums"
8355         local get_checksum="$LCTL get_param -n $cksum_param | head -n1"
8356         local checksum
8357         local i
8358
8359         [ "$ORIG_CSUM" ] || ORIG_CSUM=$(eval $get_checksum)
8360         stack_trap "wait_update $HOSTNAME '$get_checksum' $ORIG_CSUM" EXIT
8361         stack_trap "do_facet mgs $LCTL set_param -P $cksum_param=$ORIG_CSUM" \
8362                 EXIT
8363
8364         for i in 0 1; do
8365                 do_facet mgs $LCTL set_param -P $cksum_param=$i ||
8366                         error "failed to set checksum=$i on MGS"
8367                 wait_update $HOSTNAME "$get_checksum" $i
8368                 #remount
8369                 echo "remount client, checksum should be $i"
8370                 remount_client $MOUNT || error "failed to remount client"
8371                 checksum=$(eval $get_checksum)
8372                 [ $checksum -eq $i ] || error "checksum($checksum) != $i"
8373         done
8374         # remove persistent param to avoid races with checksum mountopt below
8375         do_facet mgs $LCTL set_param -P -d $cksum_param ||
8376                 error "failed to delete checksum on MGS"
8377
8378         for opt in "checksum" "nochecksum"; do
8379                 #remount with mount option
8380                 echo "remount client with option $opt, checksum should be $i"
8381                 umount_client $MOUNT || error "failed to umount client"
8382                 mount_client $MOUNT "$MOUNT_OPTS,$opt" ||
8383                         error "failed to mount client with option '$opt'"
8384                 checksum=$(eval $get_checksum)
8385                 [ $checksum -eq $i ] || error "checksum($checksum) != $i"
8386                 i=$((i - 1))
8387         done
8388
8389         remount_client $MOUNT || error "failed to remount client"
8390 }
8391 run_test 77k "enable/disable checksum correctly"
8392
8393 test_77l() {
8394         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8395         $GSS && skip_env "could not run with gss"
8396
8397         set_checksums 1
8398         stack_trap "set_checksums $ORIG_CSUM" EXIT
8399         stack_trap "set_checksum_type $ORIG_CSUM_TYPE" EXIT
8400
8401         set_checksum_type invalid && error "unexpected success of invalid checksum type"
8402
8403         $LFS setstripe -c 1 -i 0 $DIR/$tfile
8404         for algo in $CKSUM_TYPES; do
8405                 set_checksum_type $algo || error "fail to set checksum type $algo"
8406                 osc_algo=$(get_osc_checksum_type OST0000)
8407                 [ "$osc_algo" != "$algo" ] && error "checksum type is $osc_algo after setting it to $algo"
8408
8409                 # no locks, no reqs to let the connection idle
8410                 cancel_lru_locks osc
8411                 lru_resize_disable osc
8412                 wait_osc_import_state client ost1 IDLE
8413
8414                 # ensure ost1 is connected
8415                 stat $DIR/$tfile >/dev/null || error "can't stat"
8416                 wait_osc_import_state client ost1 FULL
8417
8418                 osc_algo=$(get_osc_checksum_type OST0000)
8419                 [ "$osc_algo" != "$algo" ] && error "checksum type changed from $algo to $osc_algo after reconnection"
8420         done
8421         return 0
8422 }
8423 run_test 77l "preferred checksum type is remembered after reconnected"
8424
8425 [ "$ORIG_CSUM" ] && set_checksums $ORIG_CSUM || true
8426 rm -f $F77_TMP
8427 unset F77_TMP
8428
8429 cleanup_test_78() {
8430         trap 0
8431         rm -f $DIR/$tfile
8432 }
8433
8434 test_78() { # bug 10901
8435         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8436         remote_ost || skip_env "local OST"
8437
8438         NSEQ=5
8439         F78SIZE=$(($(awk '/MemFree:/ { print $2 }' /proc/meminfo) / 1024))
8440         echo "MemFree: $F78SIZE, Max file size: $MAXFREE"
8441         MEMTOTAL=$(($(awk '/MemTotal:/ { print $2 }' /proc/meminfo) / 1024))
8442         echo "MemTotal: $MEMTOTAL"
8443
8444         # reserve 256MB of memory for the kernel and other running processes,
8445         # and then take 1/2 of the remaining memory for the read/write buffers.
8446         if [ $MEMTOTAL -gt 512 ] ;then
8447                 MEMTOTAL=$(((MEMTOTAL - 256 ) / 2))
8448         else
8449                 # for those poor memory-starved high-end clusters...
8450                 MEMTOTAL=$((MEMTOTAL / 2))
8451         fi
8452         echo "Mem to use for directio: $MEMTOTAL"
8453
8454         [[ $F78SIZE -gt $MEMTOTAL ]] && F78SIZE=$MEMTOTAL
8455         [[ $F78SIZE -gt 512 ]] && F78SIZE=512
8456         [[ $F78SIZE -gt $((MAXFREE / 1024)) ]] && F78SIZE=$((MAXFREE / 1024))
8457         SMALLESTOST=$($LFS df $DIR | grep OST | awk '{ print $4 }' | sort -n |
8458                 head -n1)
8459         echo "Smallest OST: $SMALLESTOST"
8460         [[ $SMALLESTOST -lt 10240 ]] &&
8461                 skip "too small OSTSIZE, useless to run large O_DIRECT test"
8462
8463         trap cleanup_test_78 EXIT
8464
8465         [[ $F78SIZE -gt $((SMALLESTOST * $OSTCOUNT / 1024 - 80)) ]] &&
8466                 F78SIZE=$((SMALLESTOST * $OSTCOUNT / 1024 - 80))
8467
8468         [ "$SLOW" = "no" ] && NSEQ=1 && [ $F78SIZE -gt 32 ] && F78SIZE=32
8469         echo "File size: $F78SIZE"
8470         $LFS setstripe -c $OSTCOUNT $DIR/$tfile || error "setstripe failed"
8471         for i in $(seq 1 $NSEQ); do
8472                 FSIZE=$(($F78SIZE / ($NSEQ - $i + 1)))
8473                 echo directIO rdwr round $i of $NSEQ
8474                 $DIRECTIO rdwr $DIR/$tfile 0 $FSIZE 1048576||error "rdwr failed"
8475         done
8476
8477         cleanup_test_78
8478 }
8479 run_test 78 "handle large O_DIRECT writes correctly ============"
8480
8481 test_79() { # bug 12743
8482         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8483
8484         wait_delete_completed
8485
8486         BKTOTAL=$(calc_osc_kbytes kbytestotal)
8487         BKFREE=$(calc_osc_kbytes kbytesfree)
8488         BKAVAIL=$(calc_osc_kbytes kbytesavail)
8489
8490         STRING=`df -P $MOUNT | tail -n 1 | awk '{print $2","$3","$4}'`
8491         DFTOTAL=`echo $STRING | cut -d, -f1`
8492         DFUSED=`echo $STRING  | cut -d, -f2`
8493         DFAVAIL=`echo $STRING | cut -d, -f3`
8494         DFFREE=$(($DFTOTAL - $DFUSED))
8495
8496         ALLOWANCE=$((64 * $OSTCOUNT))
8497
8498         if [ $DFTOTAL -lt $(($BKTOTAL - $ALLOWANCE)) ] ||
8499            [ $DFTOTAL -gt $(($BKTOTAL + $ALLOWANCE)) ] ; then
8500                 error "df total($DFTOTAL) mismatch OST total($BKTOTAL)"
8501         fi
8502         if [ $DFFREE -lt $(($BKFREE - $ALLOWANCE)) ] ||
8503            [ $DFFREE -gt $(($BKFREE + $ALLOWANCE)) ] ; then
8504                 error "df free($DFFREE) mismatch OST free($BKFREE)"
8505         fi
8506         if [ $DFAVAIL -lt $(($BKAVAIL - $ALLOWANCE)) ] ||
8507            [ $DFAVAIL -gt $(($BKAVAIL + $ALLOWANCE)) ] ; then
8508                 error "df avail($DFAVAIL) mismatch OST avail($BKAVAIL)"
8509         fi
8510 }
8511 run_test 79 "df report consistency check ======================="
8512
8513 test_80() { # bug 10718
8514         remote_ost_nodsh && skip "remote OST with nodsh"
8515         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8516
8517         # relax strong synchronous semantics for slow backends like ZFS
8518         local soc="obdfilter.*.sync_on_lock_cancel"
8519         local soc_old=$(do_facet ost1 lctl get_param -n $soc | head -n1)
8520         local hosts=
8521         if [ "$soc_old" != "never" ] &&
8522                 [ "$ost1_FSTYPE" != "ldiskfs" ]; then
8523                         hosts=$(for host in $(seq -f "ost%g" 1 $OSTCOUNT); do
8524                                 facet_active_host $host; done | sort -u)
8525                         do_nodes $hosts lctl set_param $soc=never
8526         fi
8527
8528         dd if=/dev/zero of=$DIR/$tfile bs=1M count=1 seek=1M
8529         sync; sleep 1; sync
8530         local BEFORE=`date +%s`
8531         cancel_lru_locks osc
8532         local AFTER=`date +%s`
8533         local DIFF=$((AFTER-BEFORE))
8534         if [ $DIFF -gt 1 ] ; then
8535                 error "elapsed for 1M@1T = $DIFF"
8536         fi
8537
8538         [ -n "$hosts" ] && do_nodes $hosts lctl set_param $soc=$soc_old
8539
8540         rm -f $DIR/$tfile
8541 }
8542 run_test 80 "Page eviction is equally fast at high offsets too  ===="
8543
8544 test_81a() { # LU-456
8545         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8546         remote_ost_nodsh && skip "remote OST with nodsh"
8547
8548         # define OBD_FAIL_OST_MAPBLK_ENOSPC    0x228
8549         # MUST OR with the OBD_FAIL_ONCE (0x80000000)
8550         do_facet ost1 lctl set_param fail_loc=0x80000228
8551
8552         # write should trigger a retry and success
8553         $LFS setstripe -i 0 -c 1 $DIR/$tfile
8554         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c
8555         RC=$?
8556         if [ $RC -ne 0 ] ; then
8557                 error "write should success, but failed for $RC"
8558         fi
8559 }
8560 run_test 81a "OST should retry write when get -ENOSPC ==============="
8561
8562 test_81b() { # LU-456
8563         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8564         remote_ost_nodsh && skip "remote OST with nodsh"
8565
8566         # define OBD_FAIL_OST_MAPBLK_ENOSPC    0x228
8567         # Don't OR with the OBD_FAIL_ONCE (0x80000000)
8568         do_facet ost1 lctl set_param fail_loc=0x228
8569
8570         # write should retry several times and return -ENOSPC finally
8571         $LFS setstripe -i 0 -c 1 $DIR/$tfile
8572         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c
8573         RC=$?
8574         ENOSPC=28
8575         if [ $RC -ne $ENOSPC ] ; then
8576                 error "dd should fail for -ENOSPC, but succeed."
8577         fi
8578 }
8579 run_test 81b "OST should return -ENOSPC when retry still fails ======="
8580
8581 test_82() { # LU-1031
8582         dd if=/dev/zero of=$DIR/$tfile bs=1M count=10
8583         local gid1=14091995
8584         local gid2=16022000
8585
8586         multiop_bg_pause $DIR/$tfile OG${gid1}_g${gid1}c || return 1
8587         local MULTIPID1=$!
8588         multiop_bg_pause $DIR/$tfile O_G${gid2}r10g${gid2}c || return 2
8589         local MULTIPID2=$!
8590         kill -USR1 $MULTIPID2
8591         sleep 2
8592         if [[ `ps h -o comm -p $MULTIPID2` == "" ]]; then
8593                 error "First grouplock does not block second one"
8594         else
8595                 echo "Second grouplock blocks first one"
8596         fi
8597         kill -USR1 $MULTIPID1
8598         wait $MULTIPID1
8599         wait $MULTIPID2
8600 }
8601 run_test 82 "Basic grouplock test"
8602
8603 test_99() {
8604         [ -z "$(which cvs 2>/dev/null)" ] && skip_env "could not find cvs"
8605
8606         test_mkdir $DIR/$tdir.cvsroot
8607         chown $RUNAS_ID $DIR/$tdir.cvsroot
8608
8609         cd $TMP
8610         $RUNAS cvs -d $DIR/$tdir.cvsroot init || error "cvs init failed"
8611
8612         cd /etc/init.d
8613         # some versions of cvs import exit(1) when asked to import links or
8614         # files they can't read.  ignore those files.
8615         local toignore=$(find . -type l -printf '-I %f\n' -o \
8616                          ! -perm /4 -printf '-I %f\n')
8617         $RUNAS cvs -d $DIR/$tdir.cvsroot import -m "nomesg" $toignore \
8618                 $tdir.reposname vtag rtag
8619
8620         cd $DIR
8621         test_mkdir $DIR/$tdir.reposname
8622         chown $RUNAS_ID $DIR/$tdir.reposname
8623         $RUNAS cvs -d $DIR/$tdir.cvsroot co $tdir.reposname
8624
8625         cd $DIR/$tdir.reposname
8626         $RUNAS touch foo99
8627         $RUNAS cvs add -m 'addmsg' foo99
8628         $RUNAS cvs update
8629         $RUNAS cvs commit -m 'nomsg' foo99
8630         rm -fr $DIR/$tdir.cvsroot
8631 }
8632 run_test 99 "cvs strange file/directory operations"
8633
8634 test_100() {
8635         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8636         [[ "$NETTYPE" =~ tcp ]] ||
8637                 skip_env "TCP secure port test, not useful for NETTYPE=$NETTYPE"
8638         remote_ost_nodsh && skip "remote OST with nodsh"
8639         remote_mds_nodsh && skip "remote MDS with nodsh"
8640         remote_servers ||
8641                 skip "useless for local single node setup"
8642
8643         netstat -tna | ( rc=1; while read PROT SND RCV LOCAL REMOTE STAT; do
8644                 [ "$PROT" != "tcp" ] && continue
8645                 RPORT=$(echo $REMOTE | cut -d: -f2)
8646                 [ "$RPORT" != "$ACCEPTOR_PORT" ] && continue
8647
8648                 rc=0
8649                 LPORT=`echo $LOCAL | cut -d: -f2`
8650                 if [ $LPORT -ge 1024 ]; then
8651                         echo "bad: $PROT $SND $RCV $LOCAL $REMOTE $STAT"
8652                         netstat -tna
8653                         error_exit "local: $LPORT > 1024, remote: $RPORT"
8654                 fi
8655         done
8656         [ "$rc" = 0 ] || error_exit "privileged port not found" )
8657 }
8658 run_test 100 "check local port using privileged port ==========="
8659
8660 function get_named_value()
8661 {
8662     local tag
8663
8664     tag=$1
8665     while read ;do
8666         line=$REPLY
8667         case $line in
8668         $tag*)
8669             echo $line | sed "s/^$tag[ ]*//"
8670             break
8671             ;;
8672         esac
8673     done
8674 }
8675
8676 export CACHE_MAX=$($LCTL get_param -n llite.*.max_cached_mb |
8677                    awk '/^max_cached_mb/ { print $2 }')
8678
8679 cleanup_101a() {
8680         $LCTL set_param -n llite.*.max_cached_mb $CACHE_MAX
8681         trap 0
8682 }
8683
8684 test_101a() {
8685         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8686
8687         local s
8688         local discard
8689         local nreads=10000
8690         local cache_limit=32
8691
8692         $LCTL set_param -n osc.*-osc*.rpc_stats 0
8693         trap cleanup_101a EXIT
8694         $LCTL set_param -n llite.*.read_ahead_stats 0
8695         $LCTL set_param -n llite.*.max_cached_mb $cache_limit
8696
8697         #
8698         # randomly read 10000 of 64K chunks from file 3x 32MB in size
8699         #
8700         echo "nreads: $nreads file size: $((cache_limit * 3))MB"
8701         $READS -f $DIR/$tfile -s$((cache_limit * 3192 * 1024)) -b65536 -C -n$nreads -t 180
8702
8703         discard=0
8704         for s in $($LCTL get_param -n llite.*.read_ahead_stats |
8705                 get_named_value 'read but discarded' | cut -d" " -f1); do
8706                         discard=$(($discard + $s))
8707         done
8708         cleanup_101a
8709
8710         $LCTL get_param osc.*-osc*.rpc_stats
8711         $LCTL get_param llite.*.read_ahead_stats
8712
8713         # Discard is generally zero, but sometimes a few random reads line up
8714         # and trigger larger readahead, which is wasted & leads to discards.
8715         if [[ $(($discard)) -gt $nreads ]]; then
8716                 error "too many ($discard) discarded pages"
8717         fi
8718         rm -f $DIR/$tfile || true
8719 }
8720 run_test 101a "check read-ahead for random reads"
8721
8722 setup_test101bc() {
8723         test_mkdir $DIR/$tdir
8724         local ssize=$1
8725         local FILE_LENGTH=$2
8726         STRIPE_OFFSET=0
8727
8728         local FILE_SIZE_MB=$((FILE_LENGTH / ssize))
8729
8730         local list=$(comma_list $(osts_nodes))
8731         set_osd_param $list '' read_cache_enable 0
8732         set_osd_param $list '' writethrough_cache_enable 0
8733
8734         trap cleanup_test101bc EXIT
8735         # prepare the read-ahead file
8736         $LFS setstripe -S $ssize -i $STRIPE_OFFSET -c $OSTCOUNT $DIR/$tfile
8737
8738         dd if=/dev/zero of=$DIR/$tfile bs=$ssize \
8739                                 count=$FILE_SIZE_MB 2> /dev/null
8740
8741 }
8742
8743 cleanup_test101bc() {
8744         trap 0
8745         rm -rf $DIR/$tdir
8746         rm -f $DIR/$tfile
8747
8748         local list=$(comma_list $(osts_nodes))
8749         set_osd_param $list '' read_cache_enable 1
8750         set_osd_param $list '' writethrough_cache_enable 1
8751 }
8752
8753 calc_total() {
8754         awk 'BEGIN{total=0}; {total+=$1}; END{print total}'
8755 }
8756
8757 ra_check_101() {
8758         local READ_SIZE=$1
8759         local STRIPE_SIZE=$2
8760         local FILE_LENGTH=$3
8761         local RA_INC=1048576
8762         local STRIDE_LENGTH=$((STRIPE_SIZE/READ_SIZE))
8763         local discard_limit=$((((STRIDE_LENGTH - 1)*3/(STRIDE_LENGTH*OSTCOUNT))* \
8764                              (STRIDE_LENGTH*OSTCOUNT - STRIDE_LENGTH)))
8765         DISCARD=$($LCTL get_param -n llite.*.read_ahead_stats |
8766                         get_named_value 'read but discarded' |
8767                         cut -d" " -f1 | calc_total)
8768         if [[ $DISCARD -gt $discard_limit ]]; then
8769                 $LCTL get_param llite.*.read_ahead_stats
8770                 error "Too many ($DISCARD) discarded pages with size (${READ_SIZE})"
8771         else
8772                 echo "Read-ahead success for size ${READ_SIZE}"
8773         fi
8774 }
8775
8776 test_101b() {
8777         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8778         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
8779
8780         local STRIPE_SIZE=1048576
8781         local STRIDE_SIZE=$((STRIPE_SIZE*OSTCOUNT))
8782
8783         if [ $SLOW == "yes" ]; then
8784                 local FILE_LENGTH=$((STRIDE_SIZE * 64))
8785         else
8786                 local FILE_LENGTH=$((STRIDE_SIZE * 8))
8787         fi
8788
8789         local ITERATION=$((FILE_LENGTH / STRIDE_SIZE))
8790
8791         # prepare the read-ahead file
8792         setup_test101bc $STRIPE_SIZE $FILE_LENGTH
8793         cancel_lru_locks osc
8794         for BIDX in 2 4 8 16 32 64 128 256
8795         do
8796                 local BSIZE=$((BIDX*4096))
8797                 local READ_COUNT=$((STRIPE_SIZE/BSIZE))
8798                 local STRIDE_LENGTH=$((STRIDE_SIZE/BSIZE))
8799                 local OFFSET=$((STRIPE_SIZE/BSIZE*(OSTCOUNT - 1)))
8800                 $LCTL set_param -n llite.*.read_ahead_stats 0
8801                 $READS -f $DIR/$tfile  -l $STRIDE_LENGTH -o $OFFSET \
8802                               -s $FILE_LENGTH -b $STRIPE_SIZE -a $READ_COUNT -n $ITERATION
8803                 cancel_lru_locks osc
8804                 ra_check_101 $BSIZE $STRIPE_SIZE $FILE_LENGTH
8805         done
8806         cleanup_test101bc
8807         true
8808 }
8809 run_test 101b "check stride-io mode read-ahead ================="
8810
8811 test_101c() {
8812         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8813
8814         local STRIPE_SIZE=1048576
8815         local FILE_LENGTH=$((STRIPE_SIZE*100))
8816         local nreads=10000
8817         local rsize=65536
8818         local osc_rpc_stats
8819
8820         setup_test101bc $STRIPE_SIZE $FILE_LENGTH
8821
8822         cancel_lru_locks osc
8823         $LCTL set_param osc.*.rpc_stats 0
8824         $READS -f $DIR/$tfile -s$FILE_LENGTH -b$rsize -n$nreads -t 180
8825         $LCTL get_param osc.*.rpc_stats
8826         for osc_rpc_stats in $($LCTL get_param -N osc.*.rpc_stats); do
8827                 local stats=$($LCTL get_param -n $osc_rpc_stats)
8828                 local lines=$(echo "$stats" | awk 'END {print NR;}')
8829                 local size
8830
8831                 if [ $lines -le 20 ]; then
8832                         echo "continue debug"
8833                         continue
8834                 fi
8835                 for size in 1 2 4 8; do
8836                         local rpc=$(echo "$stats" |
8837                                     awk '($1 == "'$size':") {print $2; exit; }')
8838                         [ $rpc != 0 ] && ((size * PAGE_SIZE < rsize)) &&
8839                                 error "Small $((size*PAGE_SIZE)) read IO $rpc!"
8840                 done
8841                 echo "$osc_rpc_stats check passed!"
8842         done
8843         cleanup_test101bc
8844         true
8845 }
8846 run_test 101c "check stripe_size aligned read-ahead ================="
8847
8848 set_read_ahead() {
8849         $LCTL get_param -n llite.*.max_read_ahead_mb | head -n 1
8850         $LCTL set_param -n llite.*.max_read_ahead_mb $1 > /dev/null 2>&1
8851 }
8852
8853 test_101d() {
8854         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8855
8856         local file=$DIR/$tfile
8857         local sz_MB=${FILESIZE_101d:-500}
8858         local ra_MB=${READAHEAD_MB:-40}
8859
8860         local free_MB=$(($(df -P $DIR | tail -n 1 | awk '{ print $4 }') / 1024))
8861         [ $free_MB -lt $sz_MB ] &&
8862                 skip "Need free space ${sz_MB}M, have ${free_MB}M"
8863
8864         echo "Create test file $file size ${sz_MB}M, ${free_MB}M free"
8865         $LFS setstripe -c -1 $file || error "setstripe failed"
8866
8867         dd if=/dev/zero of=$file bs=1M count=$sz_MB || error "dd failed"
8868         echo Cancel LRU locks on lustre client to flush the client cache
8869         cancel_lru_locks osc
8870
8871         echo Disable read-ahead
8872         local old_READAHEAD=$(set_read_ahead 0)
8873
8874         echo Reading the test file $file with read-ahead disabled
8875         local raOFF=$(do_and_time "dd if=$file of=/dev/null bs=1M count=$sz_MB")
8876
8877         echo Cancel LRU locks on lustre client to flush the client cache
8878         cancel_lru_locks osc
8879         echo Enable read-ahead with ${ra_MB}MB
8880         set_read_ahead $ra_MB
8881
8882         echo Reading the test file $file with read-ahead enabled
8883         local raON=$(do_and_time "dd if=$file of=/dev/null bs=1M count=$sz_MB")
8884
8885         echo "read-ahead disabled time read $raOFF"
8886         echo "read-ahead enabled  time read $raON"
8887
8888         set_read_ahead $old_READAHEAD
8889         rm -f $file
8890         wait_delete_completed
8891
8892         [ $raOFF -le 1 ] || [ $raON -lt $raOFF ] ||
8893                 error "readahead ${raON}s > no-readahead ${raOFF}s ${sz_MB}M"
8894 }
8895 run_test 101d "file read with and without read-ahead enabled"
8896
8897 test_101e() {
8898         [ $PARALLEL == "yes" ] && skip "skip parallel run"
8899
8900         local file=$DIR/$tfile
8901         local size_KB=500  #KB
8902         local count=100
8903         local bsize=1024
8904
8905         local free_KB=$(df -P $DIR | tail -n 1 | awk '{ print $4 }')
8906         local need_KB=$((count * size_KB))
8907         [[ $free_KB -le $need_KB ]] &&
8908                 skip_env "Need free space $need_KB, have $free_KB"
8909
8910         echo "Creating $count ${size_KB}K test files"
8911         for ((i = 0; i < $count; i++)); do
8912                 dd if=/dev/zero of=$file.$i bs=$bsize count=$size_KB 2>/dev/null
8913         done
8914
8915         echo "Cancel LRU locks on lustre client to flush the client cache"
8916         cancel_lru_locks $OSC
8917
8918         echo "Reset readahead stats"
8919         $LCTL set_param -n llite.*.read_ahead_stats 0
8920
8921         for ((i = 0; i < $count; i++)); do
8922                 dd if=$file.$i of=/dev/null bs=$bsize count=$size_KB 2>/dev/null
8923         done
8924
8925         local miss=$($LCTL get_param -n llite.*.read_ahead_stats |
8926                      get_named_value 'misses' | cut -d" " -f1 | calc_total)
8927
8928         for ((i = 0; i < $count; i++)); do
8929                 rm -rf $file.$i 2>/dev/null
8930         done
8931
8932         #10000 means 20% reads are missing in readahead
8933         [[ $miss -lt 10000 ]] ||  error "misses too much for small reads"
8934 }
8935 run_test 101e "check read-ahead for small read(1k) for small files(500k)"
8936
8937 test_101f() {
8938         which iozone || skip_env "no iozone installed"
8939
8940         local old_debug=$($LCTL get_param debug)
8941         old_debug=${old_debug#*=}
8942         $LCTL set_param debug="reada mmap"
8943
8944         # create a test file
8945         iozone -i 0 -+n -r 1m -s 128m -w -f $DIR/$tfile > /dev/null 2>&1
8946
8947         echo Cancel LRU locks on lustre client to flush the client cache
8948         cancel_lru_locks osc
8949
8950         echo Reset readahead stats
8951         $LCTL set_param -n llite.*.read_ahead_stats 0
8952
8953         echo mmap read the file with small block size
8954         iozone -i 1 -u 1 -l 1 -+n -r 32k -s 128m -B -f $DIR/$tfile \
8955                 > /dev/null 2>&1
8956
8957         echo checking missing pages
8958         $LCTL get_param llite.*.read_ahead_stats
8959         local miss=$($LCTL get_param -n llite.*.read_ahead_stats |
8960                         get_named_value 'misses' | cut -d" " -f1 | calc_total)
8961
8962         $LCTL set_param debug="$old_debug"
8963         [ $miss -lt 3 ] || error "misses too much pages ('$miss')!"
8964         rm -f $DIR/$tfile
8965 }
8966 run_test 101f "check mmap read performance"
8967
8968 test_101g_brw_size_test() {
8969         local mb=$1
8970         local pages=$((mb * 1048576 / PAGE_SIZE))
8971         local file=$DIR/$tfile
8972
8973         $LCTL set_param osc.*.max_pages_per_rpc=${mb}M ||
8974                 { error "unable to set max_pages_per_rpc=${mb}M"; return 1; }
8975         for mp in $($LCTL get_param -n osc.*.max_pages_per_rpc); do
8976                 [ $mp -ne $pages ] && error "max_pages_per_rpc $mp != $pages" &&
8977                         return 2
8978         done
8979
8980         stack_trap "rm -f $file" EXIT
8981         $LCTL set_param -n osc.*.rpc_stats=0
8982
8983         # 10 RPCs should be enough for the test
8984         local count=10
8985         dd if=/dev/zero of=$file bs=${mb}M count=$count ||
8986                 { error "dd write ${mb} MB blocks failed"; return 3; }
8987         cancel_lru_locks osc
8988         dd of=/dev/null if=$file bs=${mb}M count=$count ||
8989                 { error "dd write ${mb} MB blocks failed"; return 4; }
8990
8991         # calculate number of full-sized read and write RPCs
8992         rpcs=($($LCTL get_param -n 'osc.*.rpc_stats' |
8993                 sed -n '/pages per rpc/,/^$/p' |
8994                 awk '/'$pages':/ { reads += $2; writes += $6 }; \
8995                 END { print reads,writes }'))
8996         [ ${rpcs[0]} -ne $count ] && error "${rpcs[0]} != $count read RPCs" &&
8997                 return 5
8998         [ ${rpcs[1]} -ne $count ] && error "${rpcs[1]} != $count write RPCs" &&
8999                 return 6
9000
9001         return 0
9002 }
9003
9004 test_101g() {
9005         remote_ost_nodsh && skip "remote OST with nodsh"
9006
9007         local rpcs
9008         local osts=$(get_facets OST)
9009         local list=$(comma_list $(osts_nodes))
9010         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
9011         local brw_size="obdfilter.*.brw_size"
9012
9013         $LFS setstripe -i 0 -c 1 $DIR/$tfile
9014
9015         local orig_mb=$(do_facet ost1 $LCTL get_param -n $brw_size | head -n 1)
9016
9017         if { [ $OST1_VERSION -ge $(version_code 2.8.52) ] ||
9018                 { [ $OST1_VERSION -ge $(version_code 2.7.17) ] &&
9019                   [ $OST1_VERSION -lt $(version_code 2.7.50) ]; }; } &&
9020            { [ $CLIENT_VERSION -ge $(version_code 2.8.52) ] ||
9021                 { [ $CLIENT_VERSION -ge $(version_code 2.7.17) ] &&
9022                   [ $CLIENT_VERSION -lt $(version_code 2.7.50) ]; }; }; then
9023
9024                 [ $OST1_VERSION -ge $(version_code 2.9.52) ] &&
9025                         suffix="M"
9026
9027                 if [[ $orig_mb -lt 16 ]]; then
9028                         save_lustre_params $osts "$brw_size" > $p
9029                         do_nodes $list $LCTL set_param -n $brw_size=16$suffix ||
9030                                 error "set 16MB RPC size failed"
9031
9032                         echo "remount client to enable new RPC size"
9033                         remount_client $MOUNT || error "remount_client failed"
9034                 fi
9035
9036                 test_101g_brw_size_test 16 || error "16MB RPC test failed"
9037                 # should be able to set brw_size=12, but no rpc_stats for that
9038                 test_101g_brw_size_test 8 || error "8MB RPC test failed"
9039         fi
9040
9041         test_101g_brw_size_test 4 || error "4MB RPC test failed"
9042
9043         if [[ $orig_mb -lt 16 ]]; then
9044                 restore_lustre_params < $p
9045                 remount_client $MOUNT || error "remount_client restore failed"
9046         fi
9047
9048         rm -f $p $DIR/$tfile
9049 }
9050 run_test 101g "Big bulk(4/16 MiB) readahead"
9051
9052 test_101h() {
9053         $LFS setstripe -i 0 -c 1 $DIR/$tfile
9054
9055         dd if=/dev/zero of=$DIR/$tfile bs=1M count=70 ||
9056                 error "dd 70M file failed"
9057         echo Cancel LRU locks on lustre client to flush the client cache
9058         cancel_lru_locks osc
9059
9060         echo "Reset readahead stats"
9061         $LCTL set_param -n llite.*.read_ahead_stats 0
9062
9063         echo "Read 10M of data but cross 64M bundary"
9064         dd if=$DIR/$tfile of=/dev/null bs=10M skip=6 count=1
9065         local miss=$($LCTL get_param -n llite.*.read_ahead_stats |
9066                         get_named_value 'misses' | cut -d" " -f1 | calc_total)
9067         [ $miss -eq 1 ] || error "expected miss 1 but got $miss"
9068         rm -f $p $DIR/$tfile
9069 }
9070 run_test 101h "Readahead should cover current read window"
9071
9072 setup_test102() {
9073         test_mkdir $DIR/$tdir
9074         chown $RUNAS_ID $DIR/$tdir
9075         STRIPE_SIZE=65536
9076         STRIPE_OFFSET=1
9077         STRIPE_COUNT=$OSTCOUNT
9078         [[ $OSTCOUNT -gt 4 ]] && STRIPE_COUNT=4
9079
9080         trap cleanup_test102 EXIT
9081         cd $DIR
9082         $1 $LFS setstripe -S $STRIPE_SIZE -i $STRIPE_OFFSET -c $STRIPE_COUNT $tdir
9083         cd $DIR/$tdir
9084         for num in 1 2 3 4; do
9085                 for count in $(seq 1 $STRIPE_COUNT); do
9086                         for idx in $(seq 0 $[$STRIPE_COUNT - 1]); do
9087                                 local size=`expr $STRIPE_SIZE \* $num`
9088                                 local file=file"$num-$idx-$count"
9089                                 $1 $LFS setstripe -S $size -i $idx -c $count $file
9090                         done
9091                 done
9092         done
9093
9094         cd $DIR
9095         $1 tar cf $TMP/f102.tar $tdir --xattrs
9096 }
9097
9098 cleanup_test102() {
9099         trap 0
9100         rm -f $TMP/f102.tar
9101         rm -rf $DIR/d0.sanity/d102
9102 }
9103
9104 test_102a() {
9105         [ "$UID" != 0 ] && skip "must run as root"
9106         [ -z "$(lctl get_param -n mdc.*-mdc-*.connect_flags | grep xattr)" ] &&
9107                 skip_env "must have user_xattr"
9108
9109         [ -z "$(which setfattr 2>/dev/null)" ] &&
9110                 skip_env "could not find setfattr"
9111
9112         local testfile=$DIR/$tfile
9113
9114         touch $testfile
9115         echo "set/get xattr..."
9116         setfattr -n trusted.name1 -v value1 $testfile ||
9117                 error "setfattr -n trusted.name1=value1 $testfile failed"
9118         getfattr -n trusted.name1 $testfile 2> /dev/null |
9119           grep "trusted.name1=.value1" ||
9120                 error "$testfile missing trusted.name1=value1"
9121
9122         setfattr -n user.author1 -v author1 $testfile ||
9123                 error "setfattr -n user.author1=author1 $testfile failed"
9124         getfattr -n user.author1 $testfile 2> /dev/null |
9125           grep "user.author1=.author1" ||
9126                 error "$testfile missing trusted.author1=author1"
9127
9128         echo "listxattr..."
9129         setfattr -n trusted.name2 -v value2 $testfile ||
9130                 error "$testfile unable to set trusted.name2"
9131         setfattr -n trusted.name3 -v value3 $testfile ||
9132                 error "$testfile unable to set trusted.name3"
9133         [ $(getfattr -d -m "^trusted" $testfile 2> /dev/null |
9134             grep "trusted.name" | wc -l) -eq 3 ] ||
9135                 error "$testfile missing 3 trusted.name xattrs"
9136
9137         setfattr -n user.author2 -v author2 $testfile ||
9138                 error "$testfile unable to set user.author2"
9139         setfattr -n user.author3 -v author3 $testfile ||
9140                 error "$testfile unable to set user.author3"
9141         [ $(getfattr -d -m "^user" $testfile 2> /dev/null |
9142             grep "user.author" | wc -l) -eq 3 ] ||
9143                 error "$testfile missing 3 user.author xattrs"
9144
9145         echo "remove xattr..."
9146         setfattr -x trusted.name1 $testfile ||
9147                 error "$testfile error deleting trusted.name1"
9148         getfattr -d -m trusted $testfile 2> /dev/null | grep "trusted.name1" &&
9149                 error "$testfile did not delete trusted.name1 xattr"
9150
9151         setfattr -x user.author1 $testfile ||
9152                 error "$testfile error deleting user.author1"
9153         echo "set lustre special xattr ..."
9154         $LFS setstripe -c1 $testfile
9155         local lovea=$(getfattr -n "trusted.lov" -e hex $testfile |
9156                 awk -F "=" '/trusted.lov/ { print $2 }' )
9157         setfattr -n "trusted.lov" -v $lovea $testfile ||
9158                 error "$testfile doesn't ignore setting trusted.lov again"
9159         setfattr -n "trusted.lov" -v "invalid_value" $testfile &&
9160                 error "$testfile allow setting invalid trusted.lov"
9161         rm -f $testfile
9162 }
9163 run_test 102a "user xattr test =================================="
9164
9165 test_102b() {
9166         [ -z "$(which setfattr 2>/dev/null)" ] &&
9167                 skip_env "could not find setfattr"
9168         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
9169
9170         # b10930: get/set/list trusted.lov xattr
9171         echo "get/set/list trusted.lov xattr ..."
9172         local testfile=$DIR/$tfile
9173         $LFS setstripe -S 65536 -i 1 -c $OSTCOUNT $testfile ||
9174                 error "setstripe failed"
9175         local STRIPECOUNT=$($LFS getstripe -c $testfile) ||
9176                 error "getstripe failed"
9177         getfattr -d -m "^trusted" $testfile 2>/dev/null | grep "trusted.lov" ||
9178                 error "can't get trusted.lov from $testfile"
9179
9180         local testfile2=${testfile}2
9181         local value=$(getfattr -n trusted.lov $testfile 2>/dev/null |
9182                         grep "trusted.lov" | sed -e 's/[^=]\+=//')
9183
9184         $MCREATE $testfile2
9185         setfattr -n trusted.lov -v $value $testfile2
9186         local stripe_size=$($LFS getstripe -S $testfile2)
9187         local stripe_count=$($LFS getstripe -c $testfile2)
9188         [[ $stripe_size -eq 65536 ]] ||
9189                 error "stripe size $stripe_size != 65536"
9190         [[ $stripe_count -eq $STRIPECOUNT ]] ||
9191                 error "stripe count $stripe_count != $STRIPECOUNT"
9192         rm -f $DIR/$tfile
9193 }
9194 run_test 102b "getfattr/setfattr for trusted.lov EAs ============"
9195
9196 test_102c() {
9197         [ -z "$(which setfattr 2>/dev/null)" ] &&
9198                 skip_env "could not find setfattr"
9199         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
9200
9201         # b10930: get/set/list lustre.lov xattr
9202         echo "get/set/list lustre.lov xattr ..."
9203         test_mkdir $DIR/$tdir
9204         chown $RUNAS_ID $DIR/$tdir
9205         local testfile=$DIR/$tdir/$tfile
9206         $RUNAS $LFS setstripe -S 65536 -i 1 -c $OSTCOUNT $testfile ||
9207                 error "setstripe failed"
9208         local STRIPECOUNT=$($RUNAS $LFS getstripe -c $testfile) ||
9209                 error "getstripe failed"
9210         $RUNAS getfattr -d -m "^lustre" $testfile 2> /dev/null | \
9211         grep "lustre.lov" || error "can't get lustre.lov from $testfile"
9212
9213         local testfile2=${testfile}2
9214         local value=`getfattr -n lustre.lov $testfile 2> /dev/null | \
9215                      grep "lustre.lov" |sed -e 's/[^=]\+=//'  `
9216
9217         $RUNAS $MCREATE $testfile2
9218         $RUNAS setfattr -n lustre.lov -v $value $testfile2
9219         local stripe_size=$($RUNAS $LFS getstripe -S $testfile2)
9220         local stripe_count=$($RUNAS $LFS getstripe -c $testfile2)
9221         [ $stripe_size -eq 65536 ] || error "stripe size $stripe_size != 65536"
9222         [ $stripe_count -eq $STRIPECOUNT ] ||
9223                 error "stripe count $stripe_count != $STRIPECOUNT"
9224 }
9225 run_test 102c "non-root getfattr/setfattr for lustre.lov EAs ==========="
9226
9227 compare_stripe_info1() {
9228         local stripe_index_all_zero=true
9229
9230         for num in 1 2 3 4; do
9231                 for count in $(seq 1 $STRIPE_COUNT); do
9232                         for offset in $(seq 0 $[$STRIPE_COUNT - 1]); do
9233                                 local size=$((STRIPE_SIZE * num))
9234                                 local file=file"$num-$offset-$count"
9235                                 stripe_size=$($LFS getstripe -S $PWD/$file)
9236                                 [[ $stripe_size -ne $size ]] &&
9237                                     error "$file: size $stripe_size != $size"
9238                                 stripe_count=$($LFS getstripe -c $PWD/$file)
9239                                 # allow fewer stripes to be created, ORI-601
9240                                 [[ $stripe_count -lt $(((3 * count + 3) / 4)) ]] &&
9241                                     error "$file: count $stripe_count != $count"
9242                                 stripe_index=$($LFS getstripe -i $PWD/$file)
9243                                 [[ $stripe_index -ne 0 ]] &&
9244                                         stripe_index_all_zero=false
9245                         done
9246                 done
9247         done
9248         $stripe_index_all_zero &&
9249                 error "all files are being extracted starting from OST index 0"
9250         return 0
9251 }
9252
9253 have_xattrs_include() {
9254         tar --help | grep -q xattrs-include &&
9255                 echo --xattrs-include="lustre.*"
9256 }
9257
9258 test_102d() {
9259         [ $PARALLEL == "yes" ] && skip "skip parallel run"
9260         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
9261
9262         XINC=$(have_xattrs_include)
9263         setup_test102
9264         tar xf $TMP/f102.tar -C $DIR/$tdir --xattrs $XINC
9265         cd $DIR/$tdir/$tdir
9266         compare_stripe_info1
9267 }
9268 run_test 102d "tar restore stripe info from tarfile,not keep osts"
9269
9270 test_102f() {
9271         [ $PARALLEL == "yes" ] && skip "skip parallel run"
9272         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
9273
9274         XINC=$(have_xattrs_include)
9275         setup_test102
9276         test_mkdir $DIR/$tdir.restore
9277         cd $DIR
9278         tar cf - --xattrs $tdir | tar xf - \
9279                 -C $DIR/$tdir.restore --xattrs $XINC
9280         cd $DIR/$tdir.restore/$tdir
9281         compare_stripe_info1
9282 }
9283 run_test 102f "tar copy files, not keep osts"
9284
9285 grow_xattr() {
9286         [ -z "$(lctl get_param -n mdc.*.connect_flags | grep xattr)" ] &&
9287                 skip "must have user_xattr"
9288         [ -z "$(which setfattr 2>/dev/null)" ] &&
9289                 skip_env "could not find setfattr"
9290         [ -z "$(which getfattr 2>/dev/null)" ] &&
9291                 skip_env "could not find getfattr"
9292
9293         local xsize=${1:-1024}  # in bytes
9294         local file=$DIR/$tfile
9295         local value="$(generate_string $xsize)"
9296         local xbig=trusted.big
9297         local toobig=$2
9298
9299         touch $file
9300         log "save $xbig on $file"
9301         if [ -z "$toobig" ]
9302         then
9303                 setfattr -n $xbig -v $value $file ||
9304                         error "saving $xbig on $file failed"
9305         else
9306                 setfattr -n $xbig -v $value $file &&
9307                         error "saving $xbig on $file succeeded"
9308                 return 0
9309         fi
9310
9311         local orig=$(get_xattr_value $xbig $file)
9312         [[ "$orig" != "$value" ]] && error "$xbig different after saving $xbig"
9313
9314         local xsml=trusted.sml
9315         log "save $xsml on $file"
9316         setfattr -n $xsml -v val $file || error "saving $xsml on $file failed"
9317
9318         local new=$(get_xattr_value $xbig $file)
9319         [[ "$new" != "$orig" ]] && error "$xbig different after saving $xsml"
9320
9321         log "grow $xsml on $file"
9322         setfattr -n $xsml -v "$value" $file ||
9323                 error "growing $xsml on $file failed"
9324
9325         new=$(get_xattr_value $xbig $file)
9326         [[ "$new" != "$orig" ]] && error "$xbig different after growing $xsml"
9327         log "$xbig still valid after growing $xsml"
9328
9329         rm -f $file
9330 }
9331
9332 test_102h() { # bug 15777
9333         grow_xattr 1024
9334 }
9335 run_test 102h "grow xattr from inside inode to external block"
9336
9337 test_102ha() {
9338         large_xattr_enabled || skip_env "ea_inode feature disabled"
9339
9340         echo "setting xattr of max xattr size: $(max_xattr_size)"
9341         grow_xattr $(max_xattr_size)
9342
9343         echo "setting xattr of > max xattr size: $(max_xattr_size) + 10"
9344         echo "This should fail:"
9345         grow_xattr $(($(max_xattr_size) + 10)) 1
9346 }
9347 run_test 102ha "grow xattr from inside inode to external inode"
9348
9349 test_102i() { # bug 17038
9350         [ -z "$(which getfattr 2>/dev/null)" ] &&
9351                 skip "could not find getfattr"
9352
9353         touch $DIR/$tfile
9354         ln -s $DIR/$tfile $DIR/${tfile}link
9355         getfattr -n trusted.lov $DIR/$tfile ||
9356                 error "lgetxattr on $DIR/$tfile failed"
9357         getfattr -h -n trusted.lov $DIR/${tfile}link 2>&1 |
9358                 grep -i "no such attr" ||
9359                 error "error for lgetxattr on $DIR/${tfile}link is not ENODATA"
9360         rm -f $DIR/$tfile $DIR/${tfile}link
9361 }
9362 run_test 102i "lgetxattr test on symbolic link ============"
9363
9364 test_102j() {
9365         [ $PARALLEL == "yes" ] && skip "skip parallel run"
9366         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
9367
9368         XINC=$(have_xattrs_include)
9369         setup_test102 "$RUNAS"
9370         chown $RUNAS_ID $DIR/$tdir
9371         $RUNAS tar xf $TMP/f102.tar -C $DIR/$tdir --xattrs $XINC
9372         cd $DIR/$tdir/$tdir
9373         compare_stripe_info1 "$RUNAS"
9374 }
9375 run_test 102j "non-root tar restore stripe info from tarfile, not keep osts ==="
9376
9377 test_102k() {
9378         [ -z "$(which setfattr 2>/dev/null)" ] &&
9379                 skip "could not find setfattr"
9380
9381         touch $DIR/$tfile
9382         # b22187 just check that does not crash for regular file.
9383         setfattr -n trusted.lov $DIR/$tfile
9384         # b22187 'setfattr -n trusted.lov' should remove LOV EA for directories
9385         local test_kdir=$DIR/$tdir
9386         test_mkdir $test_kdir
9387         local default_size=$($LFS getstripe -S $test_kdir)
9388         local default_count=$($LFS getstripe -c $test_kdir)
9389         local default_offset=$($LFS getstripe -i $test_kdir)
9390         $LFS setstripe -S 65536 -i 0 -c $OSTCOUNT $test_kdir ||
9391                 error 'dir setstripe failed'
9392         setfattr -n trusted.lov $test_kdir
9393         local stripe_size=$($LFS getstripe -S $test_kdir)
9394         local stripe_count=$($LFS getstripe -c $test_kdir)
9395         local stripe_offset=$($LFS getstripe -i $test_kdir)
9396         [ $stripe_size -eq $default_size ] ||
9397                 error "stripe size $stripe_size != $default_size"
9398         [ $stripe_count -eq $default_count ] ||
9399                 error "stripe count $stripe_count != $default_count"
9400         [ $stripe_offset -eq $default_offset ] ||
9401                 error "stripe offset $stripe_offset != $default_offset"
9402         rm -rf $DIR/$tfile $test_kdir
9403 }
9404 run_test 102k "setfattr without parameter of value shouldn't cause a crash"
9405
9406 test_102l() {
9407         [ -z "$(which getfattr 2>/dev/null)" ] &&
9408                 skip "could not find getfattr"
9409
9410         # LU-532 trusted. xattr is invisible to non-root
9411         local testfile=$DIR/$tfile
9412
9413         touch $testfile
9414
9415         echo "listxattr as user..."
9416         chown $RUNAS_ID $testfile
9417         $RUNAS getfattr -d -m '.*' $testfile 2>&1 |
9418             grep -q "trusted" &&
9419                 error "$testfile trusted xattrs are user visible"
9420
9421         return 0;
9422 }
9423 run_test 102l "listxattr size test =================================="
9424
9425 test_102m() { # LU-3403 llite: error of listxattr when buffer is small
9426         local path=$DIR/$tfile
9427         touch $path
9428
9429         listxattr_size_check $path || error "listattr_size_check $path failed"
9430 }
9431 run_test 102m "Ensure listxattr fails on small bufffer ========"
9432
9433 cleanup_test102
9434
9435 getxattr() { # getxattr path name
9436         # Return the base64 encoding of the value of xattr name on path.
9437         local path=$1
9438         local name=$2
9439
9440         # # getfattr --absolute-names --encoding=base64 --name=trusted.lov $path
9441         # file: $path
9442         # trusted.lov=0s0AvRCwEAAAAGAAAAAAAAAAAEAAACAAAAAAAQAAEAA...AAAAAAAAA=
9443         #
9444         # We print just 0s0AvRCwEAAAAGAAAAAAAAAAAEAAACAAAAAAAQAAEAA...AAAAAAAAA=
9445
9446         getfattr --absolute-names --encoding=base64 --name=$name $path |
9447                 awk -F= -v name=$name '$1 == name {
9448                         print substr($0, index($0, "=") + 1);
9449         }'
9450 }
9451
9452 test_102n() { # LU-4101 mdt: protect internal xattrs
9453         [ -z "$(which setfattr 2>/dev/null)" ] &&
9454                 skip "could not find setfattr"
9455         if [ $MDS1_VERSION -lt $(version_code 2.5.50) ]
9456         then
9457                 skip "MDT < 2.5.50 allows setxattr on internal trusted xattrs"
9458         fi
9459
9460         local file0=$DIR/$tfile.0
9461         local file1=$DIR/$tfile.1
9462         local xattr0=$TMP/$tfile.0
9463         local xattr1=$TMP/$tfile.1
9464         local namelist="lov lma lmv link fid version som hsm"
9465         local name
9466         local value
9467
9468         rm -rf $file0 $file1 $xattr0 $xattr1
9469         touch $file0 $file1
9470
9471         # Get 'before' xattrs of $file1.
9472         getfattr --absolute-names --dump --match=- $file1 > $xattr0
9473
9474         [ $MDS1_VERSION -lt $(version_code 2.8.53) ] &&
9475                 namelist+=" lfsck_namespace"
9476         for name in $namelist; do
9477                 # Try to copy xattr from $file0 to $file1.
9478                 value=$(getxattr $file0 trusted.$name 2> /dev/null)
9479
9480                 setfattr --name=trusted.$name --value="$value" $file1 ||
9481                         error "setxattr 'trusted.$name' failed"
9482
9483                 # Try to set a garbage xattr.
9484                 value=0sVGhlIHF1aWNrIGJyb3duIGZveCBqdW1wcyBvdmVyIGl0c2VsZi4=
9485
9486                 if [[ x$name == "xlov" ]]; then
9487                         setfattr --name=trusted.lov --value="$value" $file1 &&
9488                         error "setxattr invalid 'trusted.lov' success"
9489                 else
9490                         setfattr --name=trusted.$name --value="$value" $file1 ||
9491                                 error "setxattr invalid 'trusted.$name' failed"
9492                 fi
9493
9494                 # Try to remove the xattr from $file1. We don't care if this
9495                 # appears to succeed or fail, we just don't want there to be
9496                 # any changes or crashes.
9497                 setfattr --remove=$trusted.$name $file1 2> /dev/null
9498         done
9499
9500         if [ $MDS1_VERSION -gt $(version_code 2.6.50) ]
9501         then
9502                 name="lfsck_ns"
9503                 # Try to copy xattr from $file0 to $file1.
9504                 value=$(getxattr $file0 trusted.$name 2> /dev/null)
9505
9506                 setfattr --name=trusted.$name --value="$value" $file1 ||
9507                         error "setxattr 'trusted.$name' failed"
9508
9509                 # Try to set a garbage xattr.
9510                 value=0sVGhlIHF1aWNrIGJyb3duIGZveCBqdW1wcyBvdmVyIGl0c2VsZi4=
9511
9512                 setfattr --name=trusted.$name --value="$value" $file1 ||
9513                         error "setxattr 'trusted.$name' failed"
9514
9515                 # Try to remove the xattr from $file1. We don't care if this
9516                 # appears to succeed or fail, we just don't want there to be
9517                 # any changes or crashes.
9518                 setfattr --remove=$trusted.$name $file1 2> /dev/null
9519         fi
9520
9521         # Get 'after' xattrs of file1.
9522         getfattr --absolute-names --dump --match=- $file1 > $xattr1
9523
9524         if ! diff $xattr0 $xattr1; then
9525                 error "before and after xattrs of '$file1' differ"
9526         fi
9527
9528         rm -rf $file0 $file1 $xattr0 $xattr1
9529
9530         return 0
9531 }
9532 run_test 102n "silently ignore setxattr on internal trusted xattrs"
9533
9534 test_102p() { # LU-4703 setxattr did not check ownership
9535         [ $MDS1_VERSION -lt $(version_code 2.5.56) ] &&
9536                 skip "MDS needs to be at least 2.5.56"
9537
9538         local testfile=$DIR/$tfile
9539
9540         touch $testfile
9541
9542         echo "setfacl as user..."
9543         $RUNAS setfacl -m "u:$RUNAS_ID:rwx" $testfile
9544         [ $? -ne 0 ] || error "setfacl by $RUNAS_ID was allowed on $testfile"
9545
9546         echo "setfattr as user..."
9547         setfacl -m "u:$RUNAS_ID:---" $testfile
9548         $RUNAS setfattr -x system.posix_acl_access $testfile
9549         [ $? -ne 0 ] || error "setfattr by $RUNAS_ID was allowed on $testfile"
9550 }
9551 run_test 102p "check setxattr(2) correctly fails without permission"
9552
9553 test_102q() {
9554         [ $MDS1_VERSION -lt $(version_code 2.6.92) ] &&
9555                 skip "MDS needs to be at least 2.6.92"
9556
9557         orphan_linkea_check $DIR/$tfile || error "orphan_linkea_check"
9558 }
9559 run_test 102q "flistxattr should not return trusted.link EAs for orphans"
9560
9561 test_102r() {
9562         [ $MDS1_VERSION -lt $(version_code 2.6.93) ] &&
9563                 skip "MDS needs to be at least 2.6.93"
9564
9565         touch $DIR/$tfile || error "touch"
9566         setfattr -n user.$(basename $tfile) $DIR/$tfile || error "setfattr"
9567         getfattr -n user.$(basename $tfile) $DIR/$tfile || error "getfattr"
9568         rm $DIR/$tfile || error "rm"
9569
9570         #normal directory
9571         mkdir -p $DIR/$tdir || error "mkdir"
9572         setfattr -n user.$(basename $tdir) $DIR/$tdir || error "setfattr dir"
9573         getfattr -n user.$(basename $tdir) $DIR/$tdir || error "getfattr dir"
9574         setfattr -x user.$(basename $tdir) $DIR/$tdir ||
9575                 error "$testfile error deleting user.author1"
9576         getfattr -d -m user.$(basename $tdir) 2> /dev/null |
9577                 grep "user.$(basename $tdir)" &&
9578                 error "$tdir did not delete user.$(basename $tdir)"
9579         rmdir $DIR/$tdir || error "rmdir"
9580
9581         #striped directory
9582         test_mkdir $DIR/$tdir
9583         setfattr -n user.$(basename $tdir) $DIR/$tdir || error "setfattr dir"
9584         getfattr -n user.$(basename $tdir) $DIR/$tdir || error "getfattr dir"
9585         setfattr -x user.$(basename $tdir) $DIR/$tdir ||
9586                 error "$testfile error deleting user.author1"
9587         getfattr -d -m user.$(basename $tdir) 2> /dev/null |
9588                 grep "user.$(basename $tdir)" &&
9589                 error "$tdir did not delete user.$(basename $tdir)"
9590         rmdir $DIR/$tdir || error "rm striped dir"
9591 }
9592 run_test 102r "set EAs with empty values"
9593
9594 test_102s() {
9595         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
9596                 skip "MDS needs to be at least 2.11.52"
9597
9598         local save="$TMP/$TESTSUITE-$TESTNAME.parameters"
9599
9600         save_lustre_params client "llite.*.xattr_cache" > $save
9601
9602         for cache in 0 1; do
9603                 lctl set_param llite.*.xattr_cache=$cache
9604
9605                 rm -f $DIR/$tfile
9606                 touch $DIR/$tfile || error "touch"
9607                 for prefix in lustre security system trusted user; do
9608                         # Note getxattr() may fail with 'Operation not
9609                         # supported' or 'No such attribute' depending
9610                         # on prefix and cache.
9611                         getfattr -n $prefix.n102s $DIR/$tfile &&
9612                                 error "getxattr '$prefix.n102s' should fail (cache = $cache)"
9613                 done
9614         done
9615
9616         restore_lustre_params < $save
9617 }
9618 run_test 102s "getting nonexistent xattrs should fail"
9619
9620 test_102t() {
9621         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
9622                 skip "MDS needs to be at least 2.11.52"
9623
9624         local save="$TMP/$TESTSUITE-$TESTNAME.parameters"
9625
9626         save_lustre_params client "llite.*.xattr_cache" > $save
9627
9628         for cache in 0 1; do
9629                 lctl set_param llite.*.xattr_cache=$cache
9630
9631                 for buf_size in 0 256; do
9632                         rm -f $DIR/$tfile
9633                         touch $DIR/$tfile || error "touch"
9634                         setfattr -n user.multiop $DIR/$tfile
9635                         $MULTIOP $DIR/$tfile oa$buf_size ||
9636                                 error "cannot get zero length xattr value (buf_size = $buf_size)"
9637                 done
9638         done
9639
9640         restore_lustre_params < $save
9641 }
9642 run_test 102t "zero length xattr values handled correctly"
9643
9644 run_acl_subtest()
9645 {
9646     $LUSTRE/tests/acl/run $LUSTRE/tests/acl/$1.test
9647     return $?
9648 }
9649
9650 test_103a() {
9651         [ "$UID" != 0 ] && skip "must run as root"
9652         $GSS && skip_env "could not run under gss"
9653         [ -z "$(lctl get_param -n mdc.*-mdc-*.connect_flags | grep acl)" ] &&
9654                 skip_env "must have acl enabled"
9655         [ -z "$(which setfacl 2>/dev/null)" ] &&
9656                 skip_env "could not find setfacl"
9657         remote_mds_nodsh && skip "remote MDS with nodsh"
9658
9659         gpasswd -a daemon bin                           # LU-5641
9660         do_facet $SINGLEMDS gpasswd -a daemon bin       # LU-5641
9661
9662         declare -a identity_old
9663
9664         for num in $(seq $MDSCOUNT); do
9665                 switch_identity $num true || identity_old[$num]=$?
9666         done
9667
9668         SAVE_UMASK=$(umask)
9669         umask 0022
9670         mkdir -p $DIR/$tdir
9671         cd $DIR/$tdir
9672
9673         echo "performing cp ..."
9674         run_acl_subtest cp || error "run_acl_subtest cp failed"
9675         echo "performing getfacl-noacl..."
9676         run_acl_subtest getfacl-noacl || error "getfacl-noacl test failed"
9677         echo "performing misc..."
9678         run_acl_subtest misc || error  "misc test failed"
9679         echo "performing permissions..."
9680         run_acl_subtest permissions || error "permissions failed"
9681         # LU-1482 mdd: Setting xattr are properly checked with and without ACLs
9682         if [ $MDS1_VERSION -gt $(version_code 2.8.55) ] ||
9683                 { [ $MDS1_VERSION -lt $(version_code 2.6) ] &&
9684                         [ $MDS1_VERSION -ge $(version_code 2.5.29) ]; }
9685         then
9686                 echo "performing permissions xattr..."
9687                 run_acl_subtest permissions_xattr ||
9688                         error "permissions_xattr failed"
9689         fi
9690         echo "performing setfacl..."
9691         run_acl_subtest setfacl || error  "setfacl test failed"
9692
9693         # inheritance test got from HP
9694         echo "performing inheritance..."
9695         cp $LUSTRE/tests/acl/make-tree . || error "cannot copy make-tree"
9696         chmod +x make-tree || error "chmod +x failed"
9697         run_acl_subtest inheritance || error "inheritance test failed"
9698         rm -f make-tree
9699
9700         echo "LU-974 ignore umask when acl is enabled..."
9701         run_acl_subtest 974 || error "LU-974 umask test failed"
9702         if [ $MDSCOUNT -ge 2 ]; then
9703                 run_acl_subtest 974_remote ||
9704                         error "LU-974 umask test failed under remote dir"
9705         fi
9706
9707         echo "LU-2561 newly created file is same size as directory..."
9708         if [ "$mds1_FSTYPE" != "zfs" ]; then
9709                 run_acl_subtest 2561 || error "LU-2561 test failed"
9710         else
9711                 run_acl_subtest 2561_zfs || error "LU-2561 zfs test failed"
9712         fi
9713
9714         run_acl_subtest 4924 || error "LU-4924 test failed"
9715
9716         cd $SAVE_PWD
9717         umask $SAVE_UMASK
9718
9719         for num in $(seq $MDSCOUNT); do
9720                 if [ "${identity_old[$num]}" = 1 ]; then
9721                         switch_identity $num false || identity_old[$num]=$?
9722                 fi
9723         done
9724 }
9725 run_test 103a "acl test"
9726
9727 test_103b() {
9728         declare -a pids
9729         local U
9730
9731         for U in {0..511}; do
9732                 {
9733                 local O=$(printf "%04o" $U)
9734
9735                 umask $(printf "%04o" $((511 ^ $O)))
9736                 $LFS setstripe -c 1 $DIR/$tfile.s$O
9737                 local S=$(printf "%04o" 0$(stat -c%a $DIR/$tfile.s$O))
9738
9739                 (( $S == ($O & 0666) )) ||
9740                         error "lfs setstripe $DIR/$tfile.s$O '$S' != '$O'"
9741
9742                 $LFS setstripe -E16M -c 1 -E1G -S4M $DIR/$tfile.p$O
9743                 S=$(printf "%04o" 0$(stat -c%a $DIR/$tfile.p$O))
9744                 (( $S == ($O & 0666) )) ||
9745                         error "lfs setstripe -E $DIR/$tfile.p$O '$S' != '$O'"
9746
9747                 $LFS setstripe -N2 -c 1 $DIR/$tfile.m$O
9748                 S=$(printf "%04o" 0$(stat -c%a $DIR/$tfile.m$O))
9749                 (( $S == ($O & 0666) )) ||
9750                         error "lfs setstripe -N2 $DIR/$tfile.m$O '$S' != '$O'"
9751                 rm -f $DIR/$tfile.[smp]$0
9752                 } &
9753                 local pid=$!
9754
9755                 # limit the concurrently running threads to 64. LU-11878
9756                 local idx=$((U % 64))
9757                 [ -z "${pids[idx]}" ] || wait ${pids[idx]}
9758                 pids[idx]=$pid
9759         done
9760         wait
9761 }
9762 run_test 103b "umask lfs setstripe"
9763
9764 test_103c() {
9765         mkdir -p $DIR/$tdir
9766         cp -rp $DIR/$tdir $DIR/$tdir.bak
9767
9768         [ -n "$(getfattr -d -m. $DIR/$tdir | grep posix_acl_default)" ] &&
9769                 error "$DIR/$tdir shouldn't contain default ACL"
9770         [ -n "$(getfattr -d -m. $DIR/$tdir.bak | grep posix_acl_default)" ] &&
9771                 error "$DIR/$tdir.bak shouldn't contain default ACL"
9772         true
9773 }
9774 run_test 103c "'cp -rp' won't set empty acl"
9775
9776 test_104a() {
9777         [ $PARALLEL == "yes" ] && skip "skip parallel run"
9778
9779         touch $DIR/$tfile
9780         lfs df || error "lfs df failed"
9781         lfs df -ih || error "lfs df -ih failed"
9782         lfs df -h $DIR || error "lfs df -h $DIR failed"
9783         lfs df -i $DIR || error "lfs df -i $DIR failed"
9784         lfs df $DIR/$tfile || error "lfs df $DIR/$tfile failed"
9785         lfs df -ih $DIR/$tfile || error "lfs df -ih $DIR/$tfile failed"
9786
9787         local OSC=$(lctl dl | grep OST0000-osc-[^M] | awk '{ print $4 }')
9788         lctl --device %$OSC deactivate
9789         lfs df || error "lfs df with deactivated OSC failed"
9790         lctl --device %$OSC activate
9791         # wait the osc back to normal
9792         wait_osc_import_ready client ost
9793
9794         lfs df || error "lfs df with reactivated OSC failed"
9795         rm -f $DIR/$tfile
9796 }
9797 run_test 104a "lfs df [-ih] [path] test ========================="
9798
9799 test_104b() {
9800         [ $PARALLEL == "yes" ] && skip "skip parallel run"
9801         [ $RUNAS_ID -eq $UID ] &&
9802                 skip_env "RUNAS_ID = UID = $UID -- skipping"
9803
9804         denied_cnt=$(($($RUNAS $LFS check servers 2>&1 |
9805                         grep "Permission denied" | wc -l)))
9806         if [ $denied_cnt -ne 0 ]; then
9807                 error "lfs check servers test failed"
9808         fi
9809 }
9810 run_test 104b "$RUNAS lfs check servers test ===================="
9811
9812 test_105a() {
9813         # doesn't work on 2.4 kernels
9814         touch $DIR/$tfile
9815         if $(flock_is_enabled); then
9816                 flocks_test 1 on -f $DIR/$tfile || error "fail flock on"
9817         else
9818                 flocks_test 1 off -f $DIR/$tfile || error "fail flock off"
9819         fi
9820         rm -f $DIR/$tfile
9821 }
9822 run_test 105a "flock when mounted without -o flock test ========"
9823
9824 test_105b() {
9825         touch $DIR/$tfile
9826         if $(flock_is_enabled); then
9827                 flocks_test 1 on -c $DIR/$tfile || error "fail flock on"
9828         else
9829                 flocks_test 1 off -c $DIR/$tfile || error "fail flock off"
9830         fi
9831         rm -f $DIR/$tfile
9832 }
9833 run_test 105b "fcntl when mounted without -o flock test ========"
9834
9835 test_105c() {
9836         touch $DIR/$tfile
9837         if $(flock_is_enabled); then
9838                 flocks_test 1 on -l $DIR/$tfile || error "fail flock on"
9839         else
9840                 flocks_test 1 off -l $DIR/$tfile || error "fail flock off"
9841         fi
9842         rm -f $DIR/$tfile
9843 }
9844 run_test 105c "lockf when mounted without -o flock test"
9845
9846 test_105d() { # bug 15924
9847         [ $PARALLEL == "yes" ] && skip "skip parallel run"
9848
9849         test_mkdir $DIR/$tdir
9850         flock_is_enabled || skip_env "mount w/o flock enabled"
9851         #define OBD_FAIL_LDLM_CP_CB_WAIT  0x315
9852         $LCTL set_param fail_loc=0x80000315
9853         flocks_test 2 $DIR/$tdir
9854 }
9855 run_test 105d "flock race (should not freeze) ========"
9856
9857 test_105e() { # bug 22660 && 22040
9858         flock_is_enabled || skip_env "mount w/o flock enabled"
9859
9860         touch $DIR/$tfile
9861         flocks_test 3 $DIR/$tfile
9862 }
9863 run_test 105e "Two conflicting flocks from same process"
9864
9865 test_106() { #bug 10921
9866         test_mkdir $DIR/$tdir
9867         $DIR/$tdir && error "exec $DIR/$tdir succeeded"
9868         chmod 777 $DIR/$tdir || error "chmod $DIR/$tdir failed"
9869 }
9870 run_test 106 "attempt exec of dir followed by chown of that dir"
9871
9872 test_107() {
9873         [ $PARALLEL == "yes" ] && skip "skip parallel run"
9874
9875         CDIR=`pwd`
9876         local file=core
9877
9878         cd $DIR
9879         rm -f $file
9880
9881         local save_pattern=$(sysctl -n kernel.core_pattern)
9882         local save_uses_pid=$(sysctl -n kernel.core_uses_pid)
9883         sysctl -w kernel.core_pattern=$file
9884         sysctl -w kernel.core_uses_pid=0
9885
9886         ulimit -c unlimited
9887         sleep 60 &
9888         SLEEPPID=$!
9889
9890         sleep 1
9891
9892         kill -s 11 $SLEEPPID
9893         wait $SLEEPPID
9894         if [ -e $file ]; then
9895                 size=`stat -c%s $file`
9896                 [ $size -eq 0 ] && error "Fail to create core file $file"
9897         else
9898                 error "Fail to create core file $file"
9899         fi
9900         rm -f $file
9901         sysctl -w kernel.core_pattern=$save_pattern
9902         sysctl -w kernel.core_uses_pid=$save_uses_pid
9903         cd $CDIR
9904 }
9905 run_test 107 "Coredump on SIG"
9906
9907 test_110() {
9908         test_mkdir $DIR/$tdir
9909         test_mkdir $DIR/$tdir/$(str_repeat 'a' 255)
9910         $LFS mkdir -c $MDSCOUNT $DIR/$tdir/$(str_repeat 'b' 256) &&
9911                 error "mkdir with 256 char should fail, but did not"
9912         touch $DIR/$tdir/$(str_repeat 'x' 255) ||
9913                 error "create with 255 char failed"
9914         touch $DIR/$tdir/$(str_repeat 'y' 256) &&
9915                 error "create with 256 char should fail, but did not"
9916
9917         ls -l $DIR/$tdir
9918         rm -rf $DIR/$tdir
9919 }
9920 run_test 110 "filename length checking"
9921
9922 #
9923 # Purpose: To verify dynamic thread (OSS) creation.
9924 #
9925 test_115() {
9926         [ $PARALLEL == "yes" ] && skip "skip parallel run"
9927         remote_ost_nodsh && skip "remote OST with nodsh"
9928
9929         # Lustre does not stop service threads once they are started.
9930         # Reset number of running threads to default.
9931         stopall
9932         setupall
9933
9934         local OSTIO_pre
9935         local save_params="$TMP/sanity-$TESTNAME.parameters"
9936
9937         # Get ll_ost_io count before I/O
9938         OSTIO_pre=$(do_facet ost1 \
9939                 "$LCTL get_param ost.OSS.ost_io.threads_started | cut -d= -f2")
9940         # Exit if lustre is not running (ll_ost_io not running).
9941         [ -z "$OSTIO_pre" ] && error "no OSS threads"
9942
9943         echo "Starting with $OSTIO_pre threads"
9944         local thread_max=$((OSTIO_pre * 2))
9945         local rpc_in_flight=$((thread_max * 2))
9946         # Number of I/O Process proposed to be started.
9947         local nfiles
9948         local facets=$(get_facets OST)
9949
9950         save_lustre_params client "osc.*OST*.max_rpcs_in_flight" > $save_params
9951         save_lustre_params $facets "ost.OSS.ost_io.threads_max" >> $save_params
9952
9953         # Set in_flight to $rpc_in_flight
9954         $LCTL set_param osc.*OST*.max_rpcs_in_flight=$rpc_in_flight ||
9955                 error "Failed to set max_rpcs_in_flight to $rpc_in_flight"
9956         nfiles=${rpc_in_flight}
9957         # Set ost thread_max to $thread_max
9958         do_facet ost1 "$LCTL set_param ost.OSS.ost_io.threads_max=$thread_max"
9959
9960         # 5 Minutes should be sufficient for max number of OSS
9961         # threads(thread_max) to be created.
9962         local timeout=300
9963
9964         # Start I/O.
9965         local WTL=${WTL:-"$LUSTRE/tests/write_time_limit"}
9966         test_mkdir $DIR/$tdir
9967         for i in $(seq $nfiles); do
9968                 local file=$DIR/$tdir/${tfile}-$i
9969                 $LFS setstripe -c -1 -i 0 $file
9970                 ($WTL $file $timeout)&
9971         done
9972
9973         # I/O Started - Wait for thread_started to reach thread_max or report
9974         # error if thread_started is more than thread_max.
9975         echo "Waiting for thread_started to reach thread_max"
9976         local thread_started=0
9977         local end_time=$((SECONDS + timeout))
9978
9979         while [ $SECONDS -le $end_time ] ; do
9980                 echo -n "."
9981                 # Get ost i/o thread_started count.
9982                 thread_started=$(do_facet ost1 \
9983                         "$LCTL get_param \
9984                         ost.OSS.ost_io.threads_started | cut -d= -f2")
9985                 # Break out if thread_started is equal/greater than thread_max
9986                 if [[ $thread_started -ge $thread_max ]]; then
9987                         echo ll_ost_io thread_started $thread_started, \
9988                                 equal/greater than thread_max $thread_max
9989                         break
9990                 fi
9991                 sleep 1
9992         done
9993
9994         # Cleanup - We have the numbers, Kill i/o jobs if running.
9995         jobcount=($(jobs -p))
9996         for i in $(seq 0 $((${#jobcount[@]}-1)))
9997         do
9998                 kill -9 ${jobcount[$i]}
9999                 if [ $? -ne 0 ] ; then
10000                         echo Warning: \
10001                         Failed to Kill \'WTL\(I/O\)\' with pid ${jobcount[$i]}
10002                 fi
10003         done
10004
10005         # Cleanup files left by WTL binary.
10006         for i in $(seq $nfiles); do
10007                 local file=$DIR/$tdir/${tfile}-$i
10008                 rm -rf $file
10009                 if [ $? -ne 0 ] ; then
10010                         echo "Warning: Failed to delete file $file"
10011                 fi
10012         done
10013
10014         restore_lustre_params <$save_params
10015         rm -f $save_params || echo "Warning: delete file '$save_params' failed"
10016
10017         # Error out if no new thread has started or Thread started is greater
10018         # than thread max.
10019         if [[ $thread_started -le $OSTIO_pre ||
10020                         $thread_started -gt $thread_max ]]; then
10021                 error "ll_ost_io: thread_started $thread_started" \
10022                       "OSTIO_pre $OSTIO_pre, thread_max $thread_max." \
10023                       "No new thread started or thread started greater " \
10024                       "than thread_max."
10025         fi
10026 }
10027 run_test 115 "verify dynamic thread creation===================="
10028
10029 free_min_max () {
10030         wait_delete_completed
10031         AVAIL=($(lctl get_param -n osc.*[oO][sS][cC]-[^M]*.kbytesavail))
10032         echo "OST kbytes available: ${AVAIL[@]}"
10033         MAXV=${AVAIL[0]}
10034         MAXI=0
10035         MINV=${AVAIL[0]}
10036         MINI=0
10037         for ((i = 0; i < ${#AVAIL[@]}; i++)); do
10038                 #echo OST $i: ${AVAIL[i]}kb
10039                 if [[ ${AVAIL[i]} -gt $MAXV ]]; then
10040                         MAXV=${AVAIL[i]}
10041                         MAXI=$i
10042                 fi
10043                 if [[ ${AVAIL[i]} -lt $MINV ]]; then
10044                         MINV=${AVAIL[i]}
10045                         MINI=$i
10046                 fi
10047         done
10048         echo "Min free space: OST $MINI: $MINV"
10049         echo "Max free space: OST $MAXI: $MAXV"
10050 }
10051
10052 test_116a() { # was previously test_116()
10053         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10054         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
10055         remote_mds_nodsh && skip "remote MDS with nodsh"
10056
10057         echo -n "Free space priority "
10058         do_facet $SINGLEMDS lctl get_param -n lo[vd].*-mdtlov.qos_prio_free |
10059                 head -n1
10060         declare -a AVAIL
10061         free_min_max
10062
10063         [ $MINV -eq 0 ] && skip "no free space in OST$MINI, skip"
10064         [ $MINV -gt 10000000 ] && skip "too much free space in OST$MINI, skip"
10065         trap simple_cleanup_common EXIT
10066
10067         # Check if we need to generate uneven OSTs
10068         test_mkdir -p $DIR/$tdir/OST${MINI}
10069         local FILL=$((MINV / 4))
10070         local DIFF=$((MAXV - MINV))
10071         local DIFF2=$((DIFF * 100 / MINV))
10072
10073         local threshold=$(do_facet $SINGLEMDS \
10074                 lctl get_param -n *.*MDT0000-mdtlov.qos_threshold_rr | head -n1)
10075         threshold=${threshold%%%}
10076         echo -n "Check for uneven OSTs: "
10077         echo -n "diff=${DIFF}KB (${DIFF2}%) must be > ${threshold}% ..."
10078
10079         if [[ $DIFF2 -gt $threshold ]]; then
10080                 echo "ok"
10081                 echo "Don't need to fill OST$MINI"
10082         else
10083                 # generate uneven OSTs. Write 2% over the QOS threshold value
10084                 echo "no"
10085                 DIFF=$((threshold - DIFF2 + 2))
10086                 DIFF2=$((MINV * DIFF / 100))
10087                 echo "Fill $DIFF% remaining space in OST$MINI with ${DIFF2}KB"
10088                 $LFS setstripe -i $MINI -c 1 $DIR/$tdir/OST${MINI} ||
10089                         error "setstripe failed"
10090                 DIFF=$((DIFF2 / 2048))
10091                 i=0
10092                 while [ $i -lt $DIFF ]; do
10093                         i=$((i + 1))
10094                         dd if=/dev/zero of=$DIR/$tdir/OST${MINI}/$tfile-$i \
10095                                 bs=2M count=1 2>/dev/null
10096                         echo -n .
10097                 done
10098                 echo .
10099                 sync
10100                 sleep_maxage
10101                 free_min_max
10102         fi
10103
10104         DIFF=$((MAXV - MINV))
10105         DIFF2=$((DIFF * 100 / MINV))
10106         echo -n "diff=$DIFF=$DIFF2% must be > $threshold% for QOS mode..."
10107         if [ $DIFF2 -gt $threshold ]; then
10108                 echo "ok"
10109         else
10110                 echo "failed - QOS mode won't be used"
10111                 simple_cleanup_common
10112                 skip "QOS imbalance criteria not met"
10113         fi
10114
10115         MINI1=$MINI
10116         MINV1=$MINV
10117         MAXI1=$MAXI
10118         MAXV1=$MAXV
10119
10120         # now fill using QOS
10121         $LFS setstripe -c 1 $DIR/$tdir
10122         FILL=$((FILL / 200))
10123         if [ $FILL -gt 600 ]; then
10124                 FILL=600
10125         fi
10126         echo "writing $FILL files to QOS-assigned OSTs"
10127         i=0
10128         while [ $i -lt $FILL ]; do
10129                 i=$((i + 1))
10130                 dd if=/dev/zero of=$DIR/$tdir/$tfile-$i bs=200k \
10131                         count=1 2>/dev/null
10132                 echo -n .
10133         done
10134         echo "wrote $i 200k files"
10135         sync
10136         sleep_maxage
10137
10138         echo "Note: free space may not be updated, so measurements might be off"
10139         free_min_max
10140         DIFF2=$((MAXV - MINV))
10141         echo "free space delta: orig $DIFF final $DIFF2"
10142         [ $DIFF2 -gt $DIFF ] && echo "delta got worse!"
10143         DIFF=$((MINV1 - ${AVAIL[$MINI1]}))
10144         echo "Wrote ${DIFF}KB to smaller OST $MINI1"
10145         DIFF2=$((MAXV1 - ${AVAIL[$MAXI1]}))
10146         echo "Wrote ${DIFF2}KB to larger OST $MAXI1"
10147         if [[ $DIFF -gt 0 ]]; then
10148                 FILL=$((DIFF2 * 100 / DIFF - 100))
10149                 echo "Wrote ${FILL}% more data to larger OST $MAXI1"
10150         fi
10151
10152         # Figure out which files were written where
10153         UUID=$(lctl get_param -n lov.${FSNAME}-clilov-*.target_obd |
10154                awk '/'$MINI1': / {print $2; exit}')
10155         echo $UUID
10156         MINC=$($LFS getstripe --ost $UUID $DIR/$tdir | grep $DIR | wc -l)
10157         echo "$MINC files created on smaller OST $MINI1"
10158         UUID=$(lctl get_param -n lov.${FSNAME}-clilov-*.target_obd |
10159                awk '/'$MAXI1': / {print $2; exit}')
10160         echo $UUID
10161         MAXC=$($LFS getstripe --ost $UUID $DIR/$tdir | grep $DIR | wc -l)
10162         echo "$MAXC files created on larger OST $MAXI1"
10163         if [[ $MINC -gt 0 ]]; then
10164                 FILL=$((MAXC * 100 / MINC - 100))
10165                 echo "Wrote ${FILL}% more files to larger OST $MAXI1"
10166         fi
10167         [[ $MAXC -gt $MINC ]] ||
10168                 error_ignore LU-9 "stripe QOS didn't balance free space"
10169         simple_cleanup_common
10170 }
10171 run_test 116a "stripe QOS: free space balance ==================="
10172
10173 test_116b() { # LU-2093
10174         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10175         remote_mds_nodsh && skip "remote MDS with nodsh"
10176
10177 #define OBD_FAIL_MDS_OSC_CREATE_FAIL     0x147
10178         local old_rr=$(do_facet $SINGLEMDS lctl get_param -n \
10179                        lo[vd].$FSNAME-MDT0000-mdtlov.qos_threshold_rr | head -1)
10180         [ -z "$old_rr" ] && skip "no QOS"
10181         do_facet $SINGLEMDS lctl set_param \
10182                 lo[vd].$FSNAME-MDT0000-mdtlov.qos_threshold_rr=0
10183         mkdir -p $DIR/$tdir
10184         do_facet $SINGLEMDS lctl set_param fail_loc=0x147
10185         createmany -o $DIR/$tdir/f- 20 || error "can't create"
10186         do_facet $SINGLEMDS lctl set_param fail_loc=0
10187         rm -rf $DIR/$tdir
10188         do_facet $SINGLEMDS lctl set_param \
10189                 lo[vd].$FSNAME-MDT0000-mdtlov.qos_threshold_rr=$old_rr
10190 }
10191 run_test 116b "QoS shouldn't LBUG if not enough OSTs found on the 2nd pass"
10192
10193 test_117() # bug 10891
10194 {
10195         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10196
10197         dd if=/dev/zero of=$DIR/$tfile bs=1M count=1
10198         #define OBD_FAIL_OST_SETATTR_CREDITS 0x21e
10199         lctl set_param fail_loc=0x21e
10200         > $DIR/$tfile || error "truncate failed"
10201         lctl set_param fail_loc=0
10202         echo "Truncate succeeded."
10203         rm -f $DIR/$tfile
10204 }
10205 run_test 117 "verify osd extend =========="
10206
10207 NO_SLOW_RESENDCOUNT=4
10208 export OLD_RESENDCOUNT=""
10209 set_resend_count () {
10210         local PROC_RESENDCOUNT="osc.${FSNAME}-OST*-osc-*.resend_count"
10211         OLD_RESENDCOUNT=$(lctl get_param -n $PROC_RESENDCOUNT | head -n1)
10212         lctl set_param -n $PROC_RESENDCOUNT $1
10213         echo resend_count is set to $(lctl get_param -n $PROC_RESENDCOUNT)
10214 }
10215
10216 # for reduce test_118* time (b=14842)
10217 [ "$SLOW" = "no" ] && set_resend_count $NO_SLOW_RESENDCOUNT
10218
10219 # Reset async IO behavior after error case
10220 reset_async() {
10221         FILE=$DIR/reset_async
10222
10223         # Ensure all OSCs are cleared
10224         $LFS setstripe -c -1 $FILE
10225         dd if=/dev/zero of=$FILE bs=64k count=$OSTCOUNT
10226         sync
10227         rm $FILE
10228 }
10229
10230 test_118a() #bug 11710
10231 {
10232         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10233
10234         reset_async
10235
10236         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c
10237         DIRTY=$(lctl get_param -n llite.*.dump_page_cache | grep -c dirty)
10238         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache | grep -c writeback)
10239
10240         if [[ $DIRTY -ne 0 || $WRITEBACK -ne 0 ]]; then
10241                 error "Dirty pages not flushed to disk, dirty=$DIRTY, writeback=$WRITEBACK"
10242                 return 1;
10243         fi
10244         rm -f $DIR/$tfile
10245 }
10246 run_test 118a "verify O_SYNC works =========="
10247
10248 test_118b()
10249 {
10250         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10251         remote_ost_nodsh && skip "remote OST with nodsh"
10252
10253         reset_async
10254
10255         #define OBD_FAIL_SRV_ENOENT 0x217
10256         set_nodes_failloc "$(osts_nodes)" 0x217
10257         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c
10258         RC=$?
10259         set_nodes_failloc "$(osts_nodes)" 0
10260         DIRTY=$(lctl get_param -n llite.*.dump_page_cache | grep -c dirty)
10261         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache |
10262                     grep -c writeback)
10263
10264         if [[ $RC -eq 0 ]]; then
10265                 error "Must return error due to dropped pages, rc=$RC"
10266                 return 1;
10267         fi
10268
10269         if [[ $DIRTY -ne 0 || $WRITEBACK -ne 0 ]]; then
10270                 error "Dirty pages not flushed to disk, dirty=$DIRTY, writeback=$WRITEBACK"
10271                 return 1;
10272         fi
10273
10274         echo "Dirty pages not leaked on ENOENT"
10275
10276         # Due to the above error the OSC will issue all RPCs syncronously
10277         # until a subsequent RPC completes successfully without error.
10278         $MULTIOP $DIR/$tfile Ow4096yc
10279         rm -f $DIR/$tfile
10280
10281         return 0
10282 }
10283 run_test 118b "Reclaim dirty pages on fatal error =========="
10284
10285 test_118c()
10286 {
10287         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10288
10289         # for 118c, restore the original resend count, LU-1940
10290         [ "$SLOW" = "no" ] && [ -n "$OLD_RESENDCOUNT" ] &&
10291                                 set_resend_count $OLD_RESENDCOUNT
10292         remote_ost_nodsh && skip "remote OST with nodsh"
10293
10294         reset_async
10295
10296         #define OBD_FAIL_OST_EROFS               0x216
10297         set_nodes_failloc "$(osts_nodes)" 0x216
10298
10299         # multiop should block due to fsync until pages are written
10300         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c &
10301         MULTIPID=$!
10302         sleep 1
10303
10304         if [[ `ps h -o comm -p $MULTIPID` != "multiop" ]]; then
10305                 error "Multiop failed to block on fsync, pid=$MULTIPID"
10306         fi
10307
10308         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache |
10309                     grep -c writeback)
10310         if [[ $WRITEBACK -eq 0 ]]; then
10311                 error "No page in writeback, writeback=$WRITEBACK"
10312         fi
10313
10314         set_nodes_failloc "$(osts_nodes)" 0
10315         wait $MULTIPID
10316         RC=$?
10317         if [[ $RC -ne 0 ]]; then
10318                 error "Multiop fsync failed, rc=$RC"
10319         fi
10320
10321         DIRTY=$(lctl get_param -n llite.*.dump_page_cache | grep -c dirty)
10322         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache |
10323                     grep -c writeback)
10324         if [[ $DIRTY -ne 0 || $WRITEBACK -ne 0 ]]; then
10325                 error "Dirty pages not flushed to disk, dirty=$DIRTY, writeback=$WRITEBACK"
10326         fi
10327
10328         rm -f $DIR/$tfile
10329         echo "Dirty pages flushed via fsync on EROFS"
10330         return 0
10331 }
10332 run_test 118c "Fsync blocks on EROFS until dirty pages are flushed =========="
10333
10334 # continue to use small resend count to reduce test_118* time (b=14842)
10335 [ "$SLOW" = "no" ] && set_resend_count $NO_SLOW_RESENDCOUNT
10336
10337 test_118d()
10338 {
10339         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10340         remote_ost_nodsh && skip "remote OST with nodsh"
10341
10342         reset_async
10343
10344         #define OBD_FAIL_OST_BRW_PAUSE_BULK
10345         set_nodes_failloc "$(osts_nodes)" 0x214
10346         # multiop should block due to fsync until pages are written
10347         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c &
10348         MULTIPID=$!
10349         sleep 1
10350
10351         if [[ `ps h -o comm -p $MULTIPID` != "multiop" ]]; then
10352                 error "Multiop failed to block on fsync, pid=$MULTIPID"
10353         fi
10354
10355         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache |
10356                     grep -c writeback)
10357         if [[ $WRITEBACK -eq 0 ]]; then
10358                 error "No page in writeback, writeback=$WRITEBACK"
10359         fi
10360
10361         wait $MULTIPID || error "Multiop fsync failed, rc=$?"
10362         set_nodes_failloc "$(osts_nodes)" 0
10363
10364         DIRTY=$(lctl get_param -n llite.*.dump_page_cache | grep -c dirty)
10365         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache |
10366                     grep -c writeback)
10367         if [[ $DIRTY -ne 0 || $WRITEBACK -ne 0 ]]; then
10368                 error "Dirty pages not flushed to disk, dirty=$DIRTY, writeback=$WRITEBACK"
10369         fi
10370
10371         rm -f $DIR/$tfile
10372         echo "Dirty pages gaurenteed flushed via fsync"
10373         return 0
10374 }
10375 run_test 118d "Fsync validation inject a delay of the bulk =========="
10376
10377 test_118f() {
10378         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10379
10380         reset_async
10381
10382         #define OBD_FAIL_OSC_BRW_PREP_REQ2        0x40a
10383         lctl set_param fail_loc=0x8000040a
10384
10385         # Should simulate EINVAL error which is fatal
10386         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c
10387         RC=$?
10388         if [[ $RC -eq 0 ]]; then
10389                 error "Must return error due to dropped pages, rc=$RC"
10390         fi
10391
10392         lctl set_param fail_loc=0x0
10393
10394         LOCKED=$(lctl get_param -n llite.*.dump_page_cache | grep -c locked)
10395         DIRTY=$(lctl get_param -n llite.*.dump_page_cache | grep -c dirty)
10396         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache |
10397                     grep -c writeback)
10398         if [[ $LOCKED -ne 0 ]]; then
10399                 error "Locked pages remain in cache, locked=$LOCKED"
10400         fi
10401
10402         if [[ $DIRTY -ne 0 || $WRITEBACK -ne 0 ]]; then
10403                 error "Dirty pages not flushed to disk, dirty=$DIRTY, writeback=$WRITEBACK"
10404         fi
10405
10406         rm -f $DIR/$tfile
10407         echo "No pages locked after fsync"
10408
10409         reset_async
10410         return 0
10411 }
10412 run_test 118f "Simulate unrecoverable OSC side error =========="
10413
10414 test_118g() {
10415         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10416
10417         reset_async
10418
10419         #define OBD_FAIL_OSC_BRW_PREP_REQ        0x406
10420         lctl set_param fail_loc=0x406
10421
10422         # simulate local -ENOMEM
10423         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c
10424         RC=$?
10425
10426         lctl set_param fail_loc=0
10427         if [[ $RC -eq 0 ]]; then
10428                 error "Must return error due to dropped pages, rc=$RC"
10429         fi
10430
10431         LOCKED=$(lctl get_param -n llite.*.dump_page_cache | grep -c locked)
10432         DIRTY=$(lctl get_param -n llite.*.dump_page_cache | grep -c dirty)
10433         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache |
10434                         grep -c writeback)
10435         if [[ $LOCKED -ne 0 ]]; then
10436                 error "Locked pages remain in cache, locked=$LOCKED"
10437         fi
10438
10439         if [[ $DIRTY -ne 0 || $WRITEBACK -ne 0 ]]; then
10440                 error "Dirty pages not flushed to disk, dirty=$DIRTY, writeback=$WRITEBACK"
10441         fi
10442
10443         rm -f $DIR/$tfile
10444         echo "No pages locked after fsync"
10445
10446         reset_async
10447         return 0
10448 }
10449 run_test 118g "Don't stay in wait if we got local -ENOMEM  =========="
10450
10451 test_118h() {
10452         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10453         remote_ost_nodsh && skip "remote OST with nodsh"
10454
10455         reset_async
10456
10457         #define OBD_FAIL_OST_BRW_WRITE_BULK      0x20e
10458         set_nodes_failloc "$(osts_nodes)" 0x20e
10459         # Should simulate ENOMEM error which is recoverable and should be handled by timeout
10460         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c
10461         RC=$?
10462
10463         set_nodes_failloc "$(osts_nodes)" 0
10464         if [[ $RC -eq 0 ]]; then
10465                 error "Must return error due to dropped pages, rc=$RC"
10466         fi
10467
10468         LOCKED=$(lctl get_param -n llite.*.dump_page_cache | grep -c locked)
10469         DIRTY=$(lctl get_param -n llite.*.dump_page_cache | grep -c dirty)
10470         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache |
10471                     grep -c writeback)
10472         if [[ $LOCKED -ne 0 ]]; then
10473                 error "Locked pages remain in cache, locked=$LOCKED"
10474         fi
10475
10476         if [[ $DIRTY -ne 0 || $WRITEBACK -ne 0 ]]; then
10477                 error "Dirty pages not flushed to disk, dirty=$DIRTY, writeback=$WRITEBACK"
10478         fi
10479
10480         rm -f $DIR/$tfile
10481         echo "No pages locked after fsync"
10482
10483         return 0
10484 }
10485 run_test 118h "Verify timeout in handling recoverables errors  =========="
10486
10487 [ "$SLOW" = "no" ] && [ -n "$OLD_RESENDCOUNT" ] && set_resend_count $OLD_RESENDCOUNT
10488
10489 test_118i() {
10490         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10491         remote_ost_nodsh && skip "remote OST with nodsh"
10492
10493         reset_async
10494
10495         #define OBD_FAIL_OST_BRW_WRITE_BULK      0x20e
10496         set_nodes_failloc "$(osts_nodes)" 0x20e
10497
10498         # Should simulate ENOMEM error which is recoverable and should be handled by timeout
10499         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c &
10500         PID=$!
10501         sleep 5
10502         set_nodes_failloc "$(osts_nodes)" 0
10503
10504         wait $PID
10505         RC=$?
10506         if [[ $RC -ne 0 ]]; then
10507                 error "got error, but should be not, rc=$RC"
10508         fi
10509
10510         LOCKED=$(lctl get_param -n llite.*.dump_page_cache | grep -c locked)
10511         DIRTY=$(lctl get_param -n llite.*.dump_page_cache | grep -c dirty)
10512         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache | grep -c writeback)
10513         if [[ $LOCKED -ne 0 ]]; then
10514                 error "Locked pages remain in cache, locked=$LOCKED"
10515         fi
10516
10517         if [[ $DIRTY -ne 0 || $WRITEBACK -ne 0 ]]; then
10518                 error "Dirty pages not flushed to disk, dirty=$DIRTY, writeback=$WRITEBACK"
10519         fi
10520
10521         rm -f $DIR/$tfile
10522         echo "No pages locked after fsync"
10523
10524         return 0
10525 }
10526 run_test 118i "Fix error before timeout in recoverable error  =========="
10527
10528 [ "$SLOW" = "no" ] && set_resend_count 4
10529
10530 test_118j() {
10531         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10532         remote_ost_nodsh && skip "remote OST with nodsh"
10533
10534         reset_async
10535
10536         #define OBD_FAIL_OST_BRW_WRITE_BULK2     0x220
10537         set_nodes_failloc "$(osts_nodes)" 0x220
10538
10539         # return -EIO from OST
10540         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:O_SYNC:w4096c
10541         RC=$?
10542         set_nodes_failloc "$(osts_nodes)" 0x0
10543         if [[ $RC -eq 0 ]]; then
10544                 error "Must return error due to dropped pages, rc=$RC"
10545         fi
10546
10547         LOCKED=$(lctl get_param -n llite.*.dump_page_cache | grep -c locked)
10548         DIRTY=$(lctl get_param -n llite.*.dump_page_cache | grep -c dirty)
10549         WRITEBACK=$(lctl get_param -n llite.*.dump_page_cache | grep -c writeback)
10550         if [[ $LOCKED -ne 0 ]]; then
10551                 error "Locked pages remain in cache, locked=$LOCKED"
10552         fi
10553
10554         # in recoverable error on OST we want resend and stay until it finished
10555         if [[ $DIRTY -ne 0 || $WRITEBACK -ne 0 ]]; then
10556                 error "Dirty pages not flushed to disk, dirty=$DIRTY, writeback=$WRITEBACK"
10557         fi
10558
10559         rm -f $DIR/$tfile
10560         echo "No pages locked after fsync"
10561
10562         return 0
10563 }
10564 run_test 118j "Simulate unrecoverable OST side error =========="
10565
10566 test_118k()
10567 {
10568         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10569         remote_ost_nodsh && skip "remote OSTs with nodsh"
10570
10571         #define OBD_FAIL_OST_BRW_WRITE_BULK      0x20e
10572         set_nodes_failloc "$(osts_nodes)" 0x20e
10573         test_mkdir $DIR/$tdir
10574
10575         for ((i=0;i<10;i++)); do
10576                 (dd if=/dev/zero of=$DIR/$tdir/$tfile-$i bs=1M count=10 || \
10577                         error "dd to $DIR/$tdir/$tfile-$i failed" )&
10578                 SLEEPPID=$!
10579                 sleep 0.500s
10580                 kill $SLEEPPID
10581                 wait $SLEEPPID
10582         done
10583
10584         set_nodes_failloc "$(osts_nodes)" 0
10585         rm -rf $DIR/$tdir
10586 }
10587 run_test 118k "bio alloc -ENOMEM and IO TERM handling ========="
10588
10589 test_118l() # LU-646
10590 {
10591         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10592
10593         test_mkdir $DIR/$tdir
10594         $MULTIOP $DIR/$tdir Dy || error "fsync dir failed"
10595         rm -rf $DIR/$tdir
10596 }
10597 run_test 118l "fsync dir"
10598
10599 test_118m() # LU-3066
10600 {
10601         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10602
10603         test_mkdir $DIR/$tdir
10604         $MULTIOP $DIR/$tdir DY || error "fdatasync dir failed"
10605         rm -rf $DIR/$tdir
10606 }
10607 run_test 118m "fdatasync dir ========="
10608
10609 [ "$SLOW" = "no" ] && [ -n "$OLD_RESENDCOUNT" ] && set_resend_count $OLD_RESENDCOUNT
10610
10611 test_118n()
10612 {
10613         local begin
10614         local end
10615
10616         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10617         remote_ost_nodsh && skip "remote OSTs with nodsh"
10618
10619         # Sleep to avoid a cached response.
10620         #define OBD_STATFS_CACHE_SECONDS 1
10621         sleep 2
10622
10623         # Inject a 10 second delay in the OST_STATFS handler.
10624         #define OBD_FAIL_OST_STATFS_DELAY 0x242
10625         set_nodes_failloc "$(osts_nodes)" 0x242
10626
10627         begin=$SECONDS
10628         stat --file-system $MOUNT > /dev/null
10629         end=$SECONDS
10630
10631         set_nodes_failloc "$(osts_nodes)" 0
10632
10633         if ((end - begin > 20)); then
10634             error "statfs took $((end - begin)) seconds, expected 10"
10635         fi
10636 }
10637 run_test 118n "statfs() sends OST_STATFS requests in parallel"
10638
10639 test_119a() # bug 11737
10640 {
10641         BSIZE=$((512 * 1024))
10642         directio write $DIR/$tfile 0 1 $BSIZE
10643         # We ask to read two blocks, which is more than a file size.
10644         # directio will indicate an error when requested and actual
10645         # sizes aren't equeal (a normal situation in this case) and
10646         # print actual read amount.
10647         NOB=`directio read $DIR/$tfile 0 2 $BSIZE | awk '/error/ {print $6}'`
10648         if [ "$NOB" != "$BSIZE" ]; then
10649                 error "read $NOB bytes instead of $BSIZE"
10650         fi
10651         rm -f $DIR/$tfile
10652 }
10653 run_test 119a "Short directIO read must return actual read amount"
10654
10655 test_119b() # bug 11737
10656 {
10657         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
10658
10659         $LFS setstripe -c 2 $DIR/$tfile || error "setstripe failed"
10660         dd if=/dev/zero of=$DIR/$tfile bs=1M count=1 seek=1 || error "dd failed"
10661         sync
10662         $MULTIOP $DIR/$tfile oO_RDONLY:O_DIRECT:r$((2048 * 1024)) ||
10663                 error "direct read failed"
10664         rm -f $DIR/$tfile
10665 }
10666 run_test 119b "Sparse directIO read must return actual read amount"
10667
10668 test_119c() # bug 13099
10669 {
10670         BSIZE=1048576
10671         directio write $DIR/$tfile 3 1 $BSIZE || error "direct write failed"
10672         directio readhole $DIR/$tfile 0 2 $BSIZE || error "reading hole failed"
10673         rm -f $DIR/$tfile
10674 }
10675 run_test 119c "Testing for direct read hitting hole"
10676
10677 test_119d() # bug 15950
10678 {
10679         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10680
10681         MAX_RPCS_IN_FLIGHT=`$LCTL get_param -n osc.*OST0000-osc-[^mM]*.max_rpcs_in_flight`
10682         $LCTL set_param -n osc.*OST0000-osc-[^mM]*.max_rpcs_in_flight 1
10683         BSIZE=1048576
10684         $LFS setstripe $DIR/$tfile -i 0 -c 1 || error "setstripe failed"
10685         $DIRECTIO write $DIR/$tfile 0 1 $BSIZE || error "first directio failed"
10686         #define OBD_FAIL_OSC_DIO_PAUSE           0x40d
10687         lctl set_param fail_loc=0x40d
10688         $DIRECTIO write $DIR/$tfile 1 4 $BSIZE &
10689         pid_dio=$!
10690         sleep 1
10691         cat $DIR/$tfile > /dev/null &
10692         lctl set_param fail_loc=0
10693         pid_reads=$!
10694         wait $pid_dio
10695         log "the DIO writes have completed, now wait for the reads (should not block very long)"
10696         sleep 2
10697         [ -n "`ps h -p $pid_reads -o comm`" ] && \
10698         error "the read rpcs have not completed in 2s"
10699         rm -f $DIR/$tfile
10700         $LCTL set_param -n osc.*OST0000-osc-[^mM]*.max_rpcs_in_flight $MAX_RPCS_IN_FLIGHT
10701 }
10702 run_test 119d "The DIO path should try to send a new rpc once one is completed"
10703
10704 test_120a() {
10705         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10706         remote_mds_nodsh && skip "remote MDS with nodsh"
10707         test_mkdir -i0 -c1 $DIR/$tdir
10708         $LCTL get_param -n mdc.*.connect_flags | grep -q early_lock_cancel ||
10709                 skip_env "no early lock cancel on server"
10710
10711         lru_resize_disable mdc
10712         lru_resize_disable osc
10713         cancel_lru_locks mdc
10714         # asynchronous object destroy at MDT could cause bl ast to client
10715         cancel_lru_locks osc
10716
10717         stat $DIR/$tdir > /dev/null
10718         can1=$(do_facet mds1 \
10719                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10720                awk '/ldlm_cancel/ {print $2}')
10721         blk1=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10722                awk '/ldlm_bl_callback/ {print $2}')
10723         test_mkdir -i0 -c1 $DIR/$tdir/d1
10724         can2=$(do_facet mds1 \
10725                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10726                awk '/ldlm_cancel/ {print $2}')
10727         blk2=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10728                awk '/ldlm_bl_callback/ {print $2}')
10729         [ $can1 -eq $can2 ] || error $((can2-can1)) "cancel RPC occured."
10730         [ $blk1 -eq $blk2 ] || error $((blk2-blk1)) "blocking RPC occured."
10731         lru_resize_enable mdc
10732         lru_resize_enable osc
10733 }
10734 run_test 120a "Early Lock Cancel: mkdir test"
10735
10736 test_120b() {
10737         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10738         remote_mds_nodsh && skip "remote MDS with nodsh"
10739         test_mkdir $DIR/$tdir
10740         $LCTL get_param -n mdc.*.connect_flags | grep -q early_lock_cancel ||
10741                 skip_env "no early lock cancel on server"
10742
10743         lru_resize_disable mdc
10744         lru_resize_disable osc
10745         cancel_lru_locks mdc
10746         stat $DIR/$tdir > /dev/null
10747         can1=$(do_facet $SINGLEMDS \
10748                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10749                awk '/ldlm_cancel/ {print $2}')
10750         blk1=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10751                awk '/ldlm_bl_callback/ {print $2}')
10752         touch $DIR/$tdir/f1
10753         can2=$(do_facet $SINGLEMDS \
10754                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10755                awk '/ldlm_cancel/ {print $2}')
10756         blk2=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10757                awk '/ldlm_bl_callback/ {print $2}')
10758         [ $can1 -eq $can2 ] || error $((can2-can1)) "cancel RPC occured."
10759         [ $blk1 -eq $blk2 ] || error $((blk2-blk1)) "blocking RPC occured."
10760         lru_resize_enable mdc
10761         lru_resize_enable osc
10762 }
10763 run_test 120b "Early Lock Cancel: create test"
10764
10765 test_120c() {
10766         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10767         remote_mds_nodsh && skip "remote MDS with nodsh"
10768         test_mkdir -i0 -c1 $DIR/$tdir
10769         $LCTL get_param -n mdc.*.connect_flags | grep -q early_lock_cancel ||
10770                 skip "no early lock cancel on server"
10771
10772         lru_resize_disable mdc
10773         lru_resize_disable osc
10774         test_mkdir -i0 -c1 $DIR/$tdir/d1
10775         test_mkdir -i0 -c1 $DIR/$tdir/d2
10776         touch $DIR/$tdir/d1/f1
10777         cancel_lru_locks mdc
10778         stat $DIR/$tdir/d1 $DIR/$tdir/d2 $DIR/$tdir/d1/f1 > /dev/null
10779         can1=$(do_facet mds1 \
10780                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10781                awk '/ldlm_cancel/ {print $2}')
10782         blk1=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10783                awk '/ldlm_bl_callback/ {print $2}')
10784         ln $DIR/$tdir/d1/f1 $DIR/$tdir/d2/f2
10785         can2=$(do_facet mds1 \
10786                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10787                awk '/ldlm_cancel/ {print $2}')
10788         blk2=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10789                awk '/ldlm_bl_callback/ {print $2}')
10790         [ $can1 -eq $can2 ] || error $((can2-can1)) "cancel RPC occured."
10791         [ $blk1 -eq $blk2 ] || error $((blk2-blk1)) "blocking RPC occured."
10792         lru_resize_enable mdc
10793         lru_resize_enable osc
10794 }
10795 run_test 120c "Early Lock Cancel: link test"
10796
10797 test_120d() {
10798         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10799         remote_mds_nodsh && skip "remote MDS with nodsh"
10800         test_mkdir -i0 -c1 $DIR/$tdir
10801         $LCTL get_param -n mdc.*.connect_flags | grep -q early_lock_cancel ||
10802                 skip_env "no early lock cancel on server"
10803
10804         lru_resize_disable mdc
10805         lru_resize_disable osc
10806         touch $DIR/$tdir
10807         cancel_lru_locks mdc
10808         stat $DIR/$tdir > /dev/null
10809         can1=$(do_facet mds1 \
10810                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10811                awk '/ldlm_cancel/ {print $2}')
10812         blk1=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10813                awk '/ldlm_bl_callback/ {print $2}')
10814         chmod a+x $DIR/$tdir
10815         can2=$(do_facet mds1 \
10816                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10817                awk '/ldlm_cancel/ {print $2}')
10818         blk2=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10819                awk '/ldlm_bl_callback/ {print $2}')
10820         [ $can1 -eq $can2 ] || error $((can2-can1)) "cancel RPC occured."
10821         [ $blk1 -eq $blk2 ] || error $((blk2-blk1)) "blocking RPC occured."
10822         lru_resize_enable mdc
10823         lru_resize_enable osc
10824 }
10825 run_test 120d "Early Lock Cancel: setattr test"
10826
10827 test_120e() {
10828         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10829         $LCTL get_param -n mdc.*.connect_flags | grep -q early_lock_cancel ||
10830                 skip_env "no early lock cancel on server"
10831         remote_mds_nodsh && skip "remote MDS with nodsh"
10832
10833         local dlmtrace_set=false
10834
10835         test_mkdir -i0 -c1 $DIR/$tdir
10836         lru_resize_disable mdc
10837         lru_resize_disable osc
10838         ! $LCTL get_param debug | grep -q dlmtrace &&
10839                 $LCTL set_param debug=+dlmtrace && dlmtrace_set=true
10840         dd if=/dev/zero of=$DIR/$tdir/f1 count=1
10841         cancel_lru_locks mdc
10842         cancel_lru_locks osc
10843         dd if=$DIR/$tdir/f1 of=/dev/null
10844         stat $DIR/$tdir $DIR/$tdir/f1 > /dev/null
10845         # XXX client can not do early lock cancel of OST lock
10846         # during unlink (LU-4206), so cancel osc lock now.
10847         sleep 2
10848         cancel_lru_locks osc
10849         can1=$(do_facet mds1 \
10850                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10851                awk '/ldlm_cancel/ {print $2}')
10852         blk1=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10853                awk '/ldlm_bl_callback/ {print $2}')
10854         unlink $DIR/$tdir/f1
10855         sleep 5
10856         can2=$(do_facet mds1 \
10857                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10858                awk '/ldlm_cancel/ {print $2}')
10859         blk2=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10860                awk '/ldlm_bl_callback/ {print $2}')
10861         [ $can1 -ne $can2 ] && error "$((can2 - can1)) cancel RPC occured" &&
10862                 $LCTL dk $TMP/cancel.debug.txt
10863         [ $blk1 -ne $blk2 ] && error "$((blk2 - blk1)) blocking RPC occured" &&
10864                 $LCTL dk $TMP/blocking.debug.txt
10865         $dlmtrace_set && $LCTL set_param debug=-dlmtrace
10866         lru_resize_enable mdc
10867         lru_resize_enable osc
10868 }
10869 run_test 120e "Early Lock Cancel: unlink test"
10870
10871 test_120f() {
10872         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10873         $LCTL get_param -n mdc.*.connect_flags | grep -q early_lock_cancel ||
10874                 skip_env "no early lock cancel on server"
10875         remote_mds_nodsh && skip "remote MDS with nodsh"
10876
10877         test_mkdir -i0 -c1 $DIR/$tdir
10878         lru_resize_disable mdc
10879         lru_resize_disable osc
10880         test_mkdir -i0 -c1 $DIR/$tdir/d1
10881         test_mkdir -i0 -c1 $DIR/$tdir/d2
10882         dd if=/dev/zero of=$DIR/$tdir/d1/f1 count=1
10883         dd if=/dev/zero of=$DIR/$tdir/d2/f2 count=1
10884         cancel_lru_locks mdc
10885         cancel_lru_locks osc
10886         dd if=$DIR/$tdir/d1/f1 of=/dev/null
10887         dd if=$DIR/$tdir/d2/f2 of=/dev/null
10888         stat $DIR/$tdir/d1 $DIR/$tdir/d2 $DIR/$tdir/d1/f1 $DIR/$tdir/d2/f2 > /dev/null
10889         # XXX client can not do early lock cancel of OST lock
10890         # during rename (LU-4206), so cancel osc lock now.
10891         sleep 2
10892         cancel_lru_locks osc
10893         can1=$(do_facet mds1 \
10894                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10895                awk '/ldlm_cancel/ {print $2}')
10896         blk1=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10897                awk '/ldlm_bl_callback/ {print $2}')
10898         mrename $DIR/$tdir/d1/f1 $DIR/$tdir/d2/f2
10899         sleep 5
10900         can2=$(do_facet mds1 \
10901                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10902                awk '/ldlm_cancel/ {print $2}')
10903         blk2=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10904                awk '/ldlm_bl_callback/ {print $2}')
10905         [ $can1 -eq $can2 ] || error $((can2-can1)) "cancel RPC occured."
10906         [ $blk1 -eq $blk2 ] || error $((blk2-blk1)) "blocking RPC occured."
10907         lru_resize_enable mdc
10908         lru_resize_enable osc
10909 }
10910 run_test 120f "Early Lock Cancel: rename test"
10911
10912 test_120g() {
10913         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10914         $LCTL get_param -n mdc.*.connect_flags | grep -q early_lock_cancel ||
10915                 skip_env "no early lock cancel on server"
10916         remote_mds_nodsh && skip "remote MDS with nodsh"
10917
10918         lru_resize_disable mdc
10919         lru_resize_disable osc
10920         count=10000
10921         echo create $count files
10922         test_mkdir $DIR/$tdir
10923         cancel_lru_locks mdc
10924         cancel_lru_locks osc
10925         t0=$(date +%s)
10926
10927         can0=$(do_facet $SINGLEMDS \
10928                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10929                awk '/ldlm_cancel/ {print $2}')
10930         blk0=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10931                awk '/ldlm_bl_callback/ {print $2}')
10932         createmany -o $DIR/$tdir/f $count
10933         sync
10934         can1=$(do_facet $SINGLEMDS \
10935                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10936                awk '/ldlm_cancel/ {print $2}')
10937         blk1=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10938                awk '/ldlm_bl_callback/ {print $2}')
10939         t1=$(date +%s)
10940         echo total: $((can1-can0)) cancels, $((blk1-blk0)) blockings
10941         echo rm $count files
10942         rm -r $DIR/$tdir
10943         sync
10944         can2=$(do_facet $SINGLEMDS \
10945                "$LCTL get_param -n ldlm.services.ldlm_canceld.stats" |
10946                awk '/ldlm_cancel/ {print $2}')
10947         blk2=$($LCTL get_param -n ldlm.services.ldlm_cbd.stats |
10948                awk '/ldlm_bl_callback/ {print $2}')
10949         t2=$(date +%s)
10950         echo total: $count removes in $((t2-t1))
10951         echo total: $((can2-can1)) cancels, $((blk2-blk1)) blockings
10952         sleep 2
10953         # wait for commitment of removal
10954         lru_resize_enable mdc
10955         lru_resize_enable osc
10956 }
10957 run_test 120g "Early Lock Cancel: performance test"
10958
10959 test_121() { #bug #10589
10960         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10961
10962         rm -rf $DIR/$tfile
10963         writes=$(LANG=C dd if=/dev/zero of=$DIR/$tfile count=1 2>&1 | awk -F '+' '/out$/ {print $1}')
10964 #define OBD_FAIL_LDLM_CANCEL_RACE        0x310
10965         lctl set_param fail_loc=0x310
10966         cancel_lru_locks osc > /dev/null
10967         reads=$(LANG=C dd if=$DIR/$tfile of=/dev/null 2>&1 | awk -F '+' '/in$/ {print $1}')
10968         lctl set_param fail_loc=0
10969         [[ $reads -eq $writes ]] ||
10970                 error "read $reads blocks, must be $writes blocks"
10971 }
10972 run_test 121 "read cancel race ========="
10973
10974 test_123a() { # was test 123, statahead(bug 11401)
10975         [ $PARALLEL == "yes" ] && skip "skip parallel run"
10976
10977         SLOWOK=0
10978         if ! grep -q "processor.*: 1" /proc/cpuinfo; then
10979                 log "testing UP system. Performance may be lower than expected."
10980                 SLOWOK=1
10981         fi
10982
10983         rm -rf $DIR/$tdir
10984         test_mkdir $DIR/$tdir
10985         NUMFREE=$(df -i -P $DIR | tail -n 1 | awk '{ print $4 }')
10986         [[ $NUMFREE -gt 100000 ]] && NUMFREE=100000 || NUMFREE=$((NUMFREE-1000))
10987         MULT=10
10988         for ((i=100, j=0; i<=$NUMFREE; j=$i, i=$((i * MULT)) )); do
10989                 createmany -o $DIR/$tdir/$tfile $j $((i - j))
10990
10991                 max=`lctl get_param -n llite.*.statahead_max | head -n 1`
10992                 lctl set_param -n llite.*.statahead_max 0
10993                 lctl get_param llite.*.statahead_max
10994                 cancel_lru_locks mdc
10995                 cancel_lru_locks osc
10996                 stime=`date +%s`
10997                 time ls -l $DIR/$tdir | wc -l
10998                 etime=`date +%s`
10999                 delta=$((etime - stime))
11000                 log "ls $i files without statahead: $delta sec"
11001                 lctl set_param llite.*.statahead_max=$max
11002
11003                 swrong=`lctl get_param -n llite.*.statahead_stats | grep "statahead wrong:" | awk '{print $3}'`
11004                 lctl get_param -n llite.*.statahead_max | grep '[0-9]'
11005                 cancel_lru_locks mdc
11006                 cancel_lru_locks osc
11007                 stime=`date +%s`
11008                 time ls -l $DIR/$tdir | wc -l
11009                 etime=`date +%s`
11010                 delta_sa=$((etime - stime))
11011                 log "ls $i files with statahead: $delta_sa sec"
11012                 lctl get_param -n llite.*.statahead_stats
11013                 ewrong=`lctl get_param -n llite.*.statahead_stats | grep "statahead wrong:" | awk '{print $3}'`
11014
11015                 [[ $swrong -lt $ewrong ]] &&
11016                         log "statahead was stopped, maybe too many locks held!"
11017                 [[ $delta -eq 0 || $delta_sa -eq 0 ]] && continue
11018
11019                 if [ $((delta_sa * 100)) -gt $((delta * 105)) -a $delta_sa -gt $((delta + 2)) ]; then
11020                     max=`lctl get_param -n llite.*.statahead_max | head -n 1`
11021                     lctl set_param -n llite.*.statahead_max 0
11022                     lctl get_param llite.*.statahead_max
11023                     cancel_lru_locks mdc
11024                     cancel_lru_locks osc
11025                     stime=`date +%s`
11026                     time ls -l $DIR/$tdir | wc -l
11027                     etime=`date +%s`
11028                     delta=$((etime - stime))
11029                     log "ls $i files again without statahead: $delta sec"
11030                     lctl set_param llite.*.statahead_max=$max
11031                     if [ $((delta_sa * 100)) -gt $((delta * 105)) -a $delta_sa -gt $((delta + 2)) ]; then
11032                         if [  $SLOWOK -eq 0 ]; then
11033                                 error "ls $i files is slower with statahead!"
11034                         else
11035                                 log "ls $i files is slower with statahead!"
11036                         fi
11037                         break
11038                     fi
11039                 fi
11040
11041                 [ $delta -gt 20 ] && break
11042                 [ $delta -gt 8 ] && MULT=$((50 / delta))
11043                 [ "$SLOW" = "no" -a $delta -gt 5 ] && break
11044         done
11045         log "ls done"
11046
11047         stime=`date +%s`
11048         rm -r $DIR/$tdir
11049         sync
11050         etime=`date +%s`
11051         delta=$((etime - stime))
11052         log "rm -r $DIR/$tdir/: $delta seconds"
11053         log "rm done"
11054         lctl get_param -n llite.*.statahead_stats
11055 }
11056 run_test 123a "verify statahead work"
11057
11058 test_123b () { # statahead(bug 15027)
11059         [ $PARALLEL == "yes" ] && skip "skip parallel run"
11060
11061         test_mkdir $DIR/$tdir
11062         createmany -o $DIR/$tdir/$tfile-%d 1000
11063
11064         cancel_lru_locks mdc
11065         cancel_lru_locks osc
11066
11067 #define OBD_FAIL_MDC_GETATTR_ENQUEUE     0x803
11068         lctl set_param fail_loc=0x80000803
11069         ls -lR $DIR/$tdir > /dev/null
11070         log "ls done"
11071         lctl set_param fail_loc=0x0
11072         lctl get_param -n llite.*.statahead_stats
11073         rm -r $DIR/$tdir
11074         sync
11075
11076 }
11077 run_test 123b "not panic with network error in statahead enqueue (bug 15027)"
11078
11079 test_124a() {
11080         [ $PARALLEL == "yes" ] && skip "skip parallel run"
11081         $LCTL get_param -n mdc.*.connect_flags | grep -q lru_resize ||
11082                 skip_env "no lru resize on server"
11083
11084         local NR=2000
11085
11086         test_mkdir $DIR/$tdir
11087
11088         log "create $NR files at $DIR/$tdir"
11089         createmany -o $DIR/$tdir/f $NR ||
11090                 error "failed to create $NR files in $DIR/$tdir"
11091
11092         cancel_lru_locks mdc
11093         ls -l $DIR/$tdir > /dev/null
11094
11095         local NSDIR=""
11096         local LRU_SIZE=0
11097         for VALUE in $($LCTL get_param ldlm.namespaces.*mdc-*.lru_size); do
11098                 local PARAM=$(echo ${VALUE[0]} | cut -d "=" -f1)
11099                 LRU_SIZE=$($LCTL get_param -n $PARAM)
11100                 if [[ $LRU_SIZE -gt $(default_lru_size) ]]; then
11101                         NSDIR=$(echo $PARAM | cut -d "." -f1-3)
11102                         log "NSDIR=$NSDIR"
11103                         log "NS=$(basename $NSDIR)"
11104                         break
11105                 fi
11106         done
11107
11108         if [[ -z "$NSDIR" || $LRU_SIZE -lt $(default_lru_size) ]]; then
11109                 skip "Not enough cached locks created!"
11110         fi
11111         log "LRU=$LRU_SIZE"
11112
11113         local SLEEP=30
11114
11115         # We know that lru resize allows one client to hold $LIMIT locks
11116         # for 10h. After that locks begin to be killed by client.
11117         local MAX_HRS=10
11118         local LIMIT=$($LCTL get_param -n $NSDIR.pool.limit)
11119         log "LIMIT=$LIMIT"
11120         if [ $LIMIT -lt $LRU_SIZE ]; then
11121                 skip "Limit is too small $LIMIT"
11122         fi
11123
11124         # Make LVF so higher that sleeping for $SLEEP is enough to _start_
11125         # killing locks. Some time was spent for creating locks. This means
11126         # that up to the moment of sleep finish we must have killed some of
11127         # them (10-100 locks). This depends on how fast ther were created.
11128         # Many of them were touched in almost the same moment and thus will
11129         # be killed in groups.
11130         local LVF=$(($MAX_HRS * 60 * 60 / $SLEEP * $LIMIT / $LRU_SIZE))
11131
11132         # Use $LRU_SIZE_B here to take into account real number of locks
11133         # created in the case of CMD, LRU_SIZE_B != $NR in most of cases
11134         local LRU_SIZE_B=$LRU_SIZE
11135         log "LVF=$LVF"
11136         local OLD_LVF=$($LCTL get_param -n $NSDIR.pool.lock_volume_factor)
11137         log "OLD_LVF=$OLD_LVF"
11138         $LCTL set_param -n $NSDIR.pool.lock_volume_factor $LVF
11139
11140         # Let's make sure that we really have some margin. Client checks
11141         # cached locks every 10 sec.
11142         SLEEP=$((SLEEP+20))
11143         log "Sleep ${SLEEP} sec"
11144         local SEC=0
11145         while ((SEC<$SLEEP)); do
11146                 echo -n "..."
11147                 sleep 5
11148                 SEC=$((SEC+5))
11149                 LRU_SIZE=$($LCTL get_param -n $NSDIR/lru_size)
11150                 echo -n "$LRU_SIZE"
11151         done
11152         echo ""
11153         $LCTL set_param -n $NSDIR.pool.lock_volume_factor $OLD_LVF
11154         local LRU_SIZE_A=$($LCTL get_param -n $NSDIR.lru_size)
11155
11156         [[ $LRU_SIZE_B -gt $LRU_SIZE_A ]] || {
11157                 error "No locks dropped in ${SLEEP}s. LRU size: $LRU_SIZE_A"
11158                 unlinkmany $DIR/$tdir/f $NR
11159                 return
11160         }
11161
11162         log "Dropped "$((LRU_SIZE_B-LRU_SIZE_A))" locks in ${SLEEP}s"
11163         log "unlink $NR files at $DIR/$tdir"
11164         unlinkmany $DIR/$tdir/f $NR
11165 }
11166 run_test 124a "lru resize ======================================="
11167
11168 get_max_pool_limit()
11169 {
11170         local limit=$($LCTL get_param \
11171                       -n ldlm.namespaces.*-MDT0000-mdc-*.pool.limit)
11172         local max=0
11173         for l in $limit; do
11174                 if [[ $l -gt $max ]]; then
11175                         max=$l
11176                 fi
11177         done
11178         echo $max
11179 }
11180
11181 test_124b() {
11182         [ $PARALLEL == "yes" ] && skip "skip parallel run"
11183         $LCTL get_param -n mdc.*.connect_flags | grep -q lru_resize ||
11184                 skip_env "no lru resize on server"
11185
11186         LIMIT=$(get_max_pool_limit)
11187
11188         NR=$(($(default_lru_size)*20))
11189         if [[ $NR -gt $LIMIT ]]; then
11190                 log "Limit lock number by $LIMIT locks"
11191                 NR=$LIMIT
11192         fi
11193
11194         IFree=$(mdsrate_inodes_available)
11195         if [ $IFree -lt $NR ]; then
11196                 log "Limit lock number by $IFree inodes"
11197                 NR=$IFree
11198         fi
11199
11200         lru_resize_disable mdc
11201         test_mkdir -p $DIR/$tdir/disable_lru_resize
11202
11203         createmany -o $DIR/$tdir/disable_lru_resize/f $NR
11204         log "doing ls -la $DIR/$tdir/disable_lru_resize 3 times"
11205         cancel_lru_locks mdc
11206         stime=`date +%s`
11207         PID=""
11208         ls -la $DIR/$tdir/disable_lru_resize > /dev/null &
11209         PID="$PID $!"
11210         sleep 2
11211         ls -la $DIR/$tdir/disable_lru_resize > /dev/null &
11212         PID="$PID $!"
11213         sleep 2
11214         ls -la $DIR/$tdir/disable_lru_resize > /dev/null &
11215         PID="$PID $!"
11216         wait $PID
11217         etime=`date +%s`
11218         nolruresize_delta=$((etime-stime))
11219         log "ls -la time: $nolruresize_delta seconds"
11220         log "lru_size = $(lctl get_param -n ldlm.namespaces.*mdc*.lru_size)"
11221         unlinkmany $DIR/$tdir/disable_lru_resize/f $NR
11222
11223         lru_resize_enable mdc
11224         test_mkdir -p $DIR/$tdir/enable_lru_resize
11225
11226         createmany -o $DIR/$tdir/enable_lru_resize/f $NR
11227         log "doing ls -la $DIR/$tdir/enable_lru_resize 3 times"
11228         cancel_lru_locks mdc
11229         stime=`date +%s`
11230         PID=""
11231         ls -la $DIR/$tdir/enable_lru_resize > /dev/null &
11232         PID="$PID $!"
11233         sleep 2
11234         ls -la $DIR/$tdir/enable_lru_resize > /dev/null &
11235         PID="$PID $!"
11236         sleep 2
11237         ls -la $DIR/$tdir/enable_lru_resize > /dev/null &
11238         PID="$PID $!"
11239         wait $PID
11240         etime=`date +%s`
11241         lruresize_delta=$((etime-stime))
11242         log "ls -la time: $lruresize_delta seconds"
11243         log "lru_size = $(lctl get_param -n ldlm.namespaces.*mdc*.lru_size)"
11244
11245         if [ $lruresize_delta -gt $nolruresize_delta ]; then
11246                 log "ls -la is $(((lruresize_delta - $nolruresize_delta) * 100 / $nolruresize_delta))% slower with lru resize enabled"
11247         elif [ $nolruresize_delta -gt $lruresize_delta ]; then
11248                 log "ls -la is $(((nolruresize_delta - $lruresize_delta) * 100 / $nolruresize_delta))% faster with lru resize enabled"
11249         else
11250                 log "lru resize performs the same with no lru resize"
11251         fi
11252         unlinkmany $DIR/$tdir/enable_lru_resize/f $NR
11253 }
11254 run_test 124b "lru resize (performance test) ======================="
11255
11256 test_124c() {
11257         [ $PARALLEL == "yes" ] && skip "skip parallel run"
11258         $LCTL get_param -n mdc.*.connect_flags | grep -q lru_resize ||
11259                 skip_env "no lru resize on server"
11260
11261         # cache ununsed locks on client
11262         local nr=100
11263         cancel_lru_locks mdc
11264         test_mkdir $DIR/$tdir
11265         createmany -o $DIR/$tdir/f $nr ||
11266                 error "failed to create $nr files in $DIR/$tdir"
11267         ls -l $DIR/$tdir > /dev/null
11268
11269         local nsdir="ldlm.namespaces.*-MDT0000-mdc-*"
11270         local unused=$($LCTL get_param -n $nsdir.lock_unused_count)
11271         local max_age=$($LCTL get_param -n $nsdir.lru_max_age)
11272         local recalc_p=$($LCTL get_param -n $nsdir.pool.recalc_period)
11273         echo "unused=$unused, max_age=$max_age, recalc_p=$recalc_p"
11274
11275         # set lru_max_age to 1 sec
11276         $LCTL set_param $nsdir.lru_max_age=1000 # milliseconds
11277         echo "sleep $((recalc_p * 2)) seconds..."
11278         sleep $((recalc_p * 2))
11279
11280         local remaining=$($LCTL get_param -n $nsdir.lock_unused_count)
11281         # restore lru_max_age
11282         $LCTL set_param -n $nsdir.lru_max_age $max_age
11283         [ $remaining -eq 0 ] || error "$remaining locks are not canceled"
11284         unlinkmany $DIR/$tdir/f $nr
11285 }
11286 run_test 124c "LRUR cancel very aged locks"
11287
11288 test_124d() {
11289         [ $PARALLEL == "yes" ] && skip "skip parallel run"
11290         $LCTL get_param -n mdc.*.connect_flags | grep -q lru_resize ||
11291                 skip_env "no lru resize on server"
11292
11293         # cache ununsed locks on client
11294         local nr=100
11295
11296         lru_resize_disable mdc
11297         stack_trap "lru_resize_enable mdc" EXIT
11298
11299         cancel_lru_locks mdc
11300
11301         # asynchronous object destroy at MDT could cause bl ast to client
11302         test_mkdir $DIR/$tdir
11303         createmany -o $DIR/$tdir/f $nr ||
11304                 error "failed to create $nr files in $DIR/$tdir"
11305         stack_trap "unlinkmany $DIR/$tdir/f $nr" EXIT
11306
11307         ls -l $DIR/$tdir > /dev/null
11308
11309         local nsdir="ldlm.namespaces.*-MDT0000-mdc-*"
11310         local unused=$($LCTL get_param -n $nsdir.lock_unused_count)
11311         local max_age=$($LCTL get_param -n $nsdir.lru_max_age)
11312         local recalc_p=$($LCTL get_param -n $nsdir.pool.recalc_period)
11313
11314         echo "unused=$unused, max_age=$max_age, recalc_p=$recalc_p"
11315
11316         # set lru_max_age to 1 sec
11317         $LCTL set_param $nsdir.lru_max_age=1000 # milliseconds
11318         stack_trap "$LCTL set_param -n $nsdir.lru_max_age $max_age" EXIT
11319
11320         echo "sleep $((recalc_p * 2)) seconds..."
11321         sleep $((recalc_p * 2))
11322
11323         local remaining=$($LCTL get_param -n $nsdir.lock_unused_count)
11324
11325         [ $remaining -eq 0 ] || error "$remaining locks are not canceled"
11326 }
11327 run_test 124d "cancel very aged locks if lru-resize diasbaled"
11328
11329 test_125() { # 13358
11330         $LCTL get_param -n llite.*.client_type | grep -q local ||
11331                 skip "must run as local client"
11332         $LCTL get_param -n mdc.*-mdc-*.connect_flags | grep -q acl ||
11333                 skip_env "must have acl enabled"
11334         [ -z "$(which setfacl)" ] && skip_env "must have setfacl tool"
11335
11336         test_mkdir $DIR/$tdir
11337         $LFS setstripe -S 65536 -c -1 $DIR/$tdir || error "setstripe failed"
11338         setfacl -R -m u:bin:rwx $DIR/$tdir || error "setfacl $DIR/$tdir failed"
11339         ls -ld $DIR/$tdir || error "cannot access $DIR/$tdir"
11340 }
11341 run_test 125 "don't return EPROTO when a dir has a non-default striping and ACLs"
11342
11343 test_126() { # bug 12829/13455
11344         $GSS && skip_env "must run as gss disabled"
11345         $LCTL get_param -n llite.*.client_type | grep -q local ||
11346                 skip "must run as local client"
11347         [ "$UID" != 0 ] && skip "must run as root, not UID $UID"
11348
11349         $RUNAS -u 0 -g 1 touch $DIR/$tfile || error "touch failed"
11350         gid=`ls -n $DIR/$tfile | awk '{print $4}'`
11351         rm -f $DIR/$tfile
11352         [ $gid -eq "1" ] || error "gid is set to" $gid "instead of 1"
11353 }
11354 run_test 126 "check that the fsgid provided by the client is taken into account"
11355
11356 test_127a() { # bug 15521
11357         [ $PARALLEL == "yes" ] && skip "skip parallel run"
11358
11359         $LFS setstripe -i 0 -c 1 $DIR/$tfile || error "setstripe failed"
11360         $LCTL set_param osc.*.stats=0
11361         FSIZE=$((2048 * 1024))
11362         dd if=/dev/zero of=$DIR/$tfile bs=$FSIZE count=1
11363         cancel_lru_locks osc
11364         dd if=$DIR/$tfile of=/dev/null bs=$FSIZE
11365
11366         $LCTL get_param osc.*0000-osc-*.stats | grep samples > $DIR/${tfile}.tmp
11367         while read NAME COUNT SAMP UNIT MIN MAX SUM SUMSQ; do
11368                 echo "got $COUNT $NAME"
11369                 [ ! $MIN ] && error "Missing min value for $NAME proc entry"
11370                 eval $NAME=$COUNT || error "Wrong proc format"
11371
11372                 case $NAME in
11373                         read_bytes|write_bytes)
11374                         [ $MIN -lt 4096 ] && error "min is too small: $MIN"
11375                         [ $MIN -gt $FSIZE ] && error "min is too big: $MIN"
11376                         [ $MAX -lt 4096 ] && error "max is too small: $MAX"
11377                         [ $MAX -gt $FSIZE ] && error "max is too big: $MAX"
11378                         [ $SUM -ne $FSIZE ] && error "sum is wrong: $SUM"
11379                         [ $SUMSQ -lt $(((FSIZE /4096) * (4096 * 4096))) ] &&
11380                                 error "sumsquare is too small: $SUMSQ"
11381                         [ $SUMSQ -gt $((FSIZE * FSIZE)) ] &&
11382                                 error "sumsquare is too big: $SUMSQ"
11383                         ;;
11384                         *) ;;
11385                 esac
11386         done < $DIR/${tfile}.tmp
11387
11388         #check that we actually got some stats
11389         [ "$read_bytes" ] || error "Missing read_bytes stats"
11390         [ "$write_bytes" ] || error "Missing write_bytes stats"
11391         [ "$read_bytes" != 0 ] || error "no read done"
11392         [ "$write_bytes" != 0 ] || error "no write done"
11393 }
11394 run_test 127a "verify the client stats are sane"
11395
11396 test_127b() { # bug LU-333
11397         [ $PARALLEL == "yes" ] && skip "skip parallel run"
11398         local name count samp unit min max sum sumsq
11399
11400         $LCTL set_param llite.*.stats=0
11401
11402         # perform 2 reads and writes so MAX is different from SUM.
11403         dd if=/dev/zero of=$DIR/$tfile bs=$PAGE_SIZE count=1
11404         dd if=/dev/zero of=$DIR/$tfile bs=$PAGE_SIZE count=1
11405         cancel_lru_locks osc
11406         dd if=$DIR/$tfile of=/dev/null bs=$PAGE_SIZE count=1
11407         dd if=$DIR/$tfile of=/dev/null bs=$PAGE_SIZE count=1
11408
11409         $LCTL get_param llite.*.stats | grep samples > $TMP/$tfile.tmp
11410         while read name count samp unit min max sum sumsq; do
11411                 echo "got $count $name"
11412                 eval $name=$count || error "Wrong proc format"
11413
11414                 case $name in
11415                 read_bytes)
11416                         [ $count -ne 2 ] && error "count is not 2: $count"
11417                         [ $min -ne $PAGE_SIZE ] &&
11418                                 error "min is not $PAGE_SIZE: $min"
11419                         [ $max -ne $PAGE_SIZE ] &&
11420                                 error "max is incorrect: $max"
11421                         [ $sum -ne $((PAGE_SIZE * 2)) ] &&
11422                                 error "sum is wrong: $sum"
11423                         ;;
11424                 write_bytes)
11425                         [ $count -ne 2 ] && error "count is not 2: $count"
11426                         [ $min -ne $PAGE_SIZE ] &&
11427                                 error "min is not $PAGE_SIZE: $min"
11428                         [ $max -ne $PAGE_SIZE ] &&
11429                                 error "max is incorrect: $max"
11430                         [ $sum -ne $((PAGE_SIZE * 2)) ] &&
11431                                 error "sum is wrong: $sum"
11432                         ;;
11433                 *) ;;
11434                 esac
11435         done < $TMP/$tfile.tmp
11436
11437         #check that we actually got some stats
11438         [ "$read_bytes" ] || error "Missing read_bytes stats"
11439         [ "$write_bytes" ] || error "Missing write_bytes stats"
11440         [ "$read_bytes" != 0 ] || error "no read done"
11441         [ "$write_bytes" != 0 ] || error "no write done"
11442
11443         rm -f $TMP/${tfile}.tmp
11444 }
11445 run_test 127b "verify the llite client stats are sane"
11446
11447 test_127c() { # LU-12394
11448         [ "$OSTCOUNT" -lt "2" ] && skip_env "needs >= 2 OSTs"
11449         local size
11450         local bsize
11451         local reads
11452         local writes
11453         local count
11454
11455         $LCTL set_param llite.*.extents_stats=1
11456         stack_trap "$LCTL set_param llite.*.extents_stats=0" EXIT
11457
11458         # Use two stripes so there is enough space in default config
11459         $LFS setstripe -c 2 $DIR/$tfile
11460
11461         # Extent stats start at 0-4K and go in power of two buckets
11462         # LL_HIST_START = 12 --> 2^12 = 4K
11463         # We do 3K*2^i, so 3K, 6K, 12K, 24K... hitting each bucket.
11464         # We do not do buckets larger than 64 MiB to avoid ENOSPC issues on
11465         # small configs
11466         for size in 3K 6K 12K 24K 48K 96K 192K 384K 768K 1536K 3M 6M 12M 24M 48M;
11467                 do
11468                 # Write and read, 2x each, second time at a non-zero offset
11469                 dd if=/dev/zero of=$DIR/$tfile bs=$size count=1
11470                 dd if=/dev/zero of=$DIR/$tfile bs=$size count=1 seek=10
11471                 dd if=$DIR/$tfile of=/dev/null bs=$size count=1
11472                 dd if=$DIR/$tfile of=/dev/null bs=$size count=1 seek=10
11473                 rm -f $DIR/$tfile
11474         done
11475
11476         $LCTL get_param llite.*.extents_stats
11477
11478         count=2
11479         for bsize in 4K 8K 16K 32K 64K 128K 256K 512K 1M 2M 4M 8M 16M 32M 64M;
11480                 do
11481                 local bucket=$($LCTL get_param -n llite.*.extents_stats |
11482                                 grep -m 1 $bsize)
11483                 reads=$(echo $bucket | awk '{print $5}')
11484                 writes=$(echo $bucket | awk '{print $9}')
11485                 [ "$reads" -eq $count ] ||
11486                         error "$reads reads in < $bsize bucket, expect $count"
11487                 [ "$writes" -eq $count ] ||
11488                         error "$writes writes in < $bsize bucket, expect $count"
11489         done
11490
11491         # Test mmap write and read
11492         $LCTL set_param llite.*.extents_stats=c
11493         size=512
11494         dd if=/dev/zero of=$DIR/$tfile bs=${size}K count=1
11495         $MULTIOP $DIR/$tfile OSMRUc || error "$MULTIOP $DIR/$tfile failed"
11496         $MULTIOP $DIR/$tfile OSMWUc || error "$MULTIOP $DIR/$tfile failed"
11497
11498         $LCTL get_param llite.*.extents_stats
11499
11500         count=$(((size*1024) / PAGE_SIZE))
11501
11502         bsize=$((2 * PAGE_SIZE / 1024))K
11503
11504         bucket=$($LCTL get_param -n llite.*.extents_stats |
11505                         grep -m 1 $bsize)
11506         reads=$(echo $bucket | awk '{print $5}')
11507         writes=$(echo $bucket | awk '{print $9}')
11508         # mmap writes fault in the page first, creating an additonal read
11509         [ "$reads" -eq $((2 * count)) ] ||
11510                 error "$reads reads in < $bsize bucket, expect $count"
11511         [ "$writes" -eq $count ] ||
11512                 error "$writes writes in < $bsize bucket, expect $count"
11513 }
11514 run_test 127c "test llite extent stats with regular & mmap i/o"
11515
11516 test_128() { # bug 15212
11517         touch $DIR/$tfile
11518         $LFS 2>&1 <<-EOF | tee $TMP/$tfile.log
11519                 find $DIR/$tfile
11520                 find $DIR/$tfile
11521         EOF
11522
11523         result=$(grep error $TMP/$tfile.log)
11524         rm -f $DIR/$tfile $TMP/$tfile.log
11525         [ -z "$result" ] ||
11526                 error "consecutive find's under interactive lfs failed"
11527 }
11528 run_test 128 "interactive lfs for 2 consecutive find's"
11529
11530 set_dir_limits () {
11531         local mntdev
11532         local canondev
11533         local node
11534
11535         local ldproc=/proc/fs/ldiskfs
11536         local facets=$(get_facets MDS)
11537
11538         for facet in ${facets//,/ }; do
11539                 canondev=$(ldiskfs_canon \
11540                            *.$(convert_facet2label $facet).mntdev $facet)
11541                 do_facet $facet "test -e $ldproc/$canondev/max_dir_size" ||
11542                         ldproc=/sys/fs/ldiskfs
11543                 do_facet $facet "echo $1 >$ldproc/$canondev/max_dir_size"
11544                 do_facet $facet "echo $2 >$ldproc/$canondev/warning_dir_size"
11545         done
11546 }
11547
11548 check_mds_dmesg() {
11549         local facets=$(get_facets MDS)
11550         for facet in ${facets//,/ }; do
11551                 do_facet $facet "dmesg | tail -3 | grep -q $1" && return 0
11552         done
11553         return 1
11554 }
11555
11556 test_129() {
11557         [ $PARALLEL == "yes" ] && skip "skip parallel run"
11558         [[ $MDS1_VERSION -ge $(version_code 2.5.56) ]] ||
11559                 skip "Need MDS version with at least 2.5.56"
11560         if [ "$mds1_FSTYPE" != ldiskfs ]; then
11561                 skip_env "ldiskfs only test"
11562         fi
11563         remote_mds_nodsh && skip "remote MDS with nodsh"
11564
11565         local ENOSPC=28
11566         local EFBIG=27
11567         local has_warning=false
11568
11569         rm -rf $DIR/$tdir
11570         mkdir -p $DIR/$tdir
11571
11572         # block size of mds1
11573         local maxsize=$(($($LCTL get_param -n mdc.*MDT0000*.blocksize) * 5))
11574         set_dir_limits $maxsize $maxsize
11575         local dirsize=$(stat -c%s "$DIR/$tdir")
11576         local nfiles=0
11577         while [[ $dirsize -le $maxsize ]]; do
11578                 $MULTIOP $DIR/$tdir/file_base_$nfiles Oc
11579                 rc=$?
11580                 if ! $has_warning; then
11581                         check_mds_dmesg '"is approaching"' && has_warning=true
11582                 fi
11583                 # check two errors:
11584                 # ENOSPC for new ext4 max_dir_size (kernel commit df981d03ee)
11585                 # EFBIG for previous versions included in ldiskfs series
11586                 if [ $rc -eq $EFBIG ] || [ $rc -eq $ENOSPC ]; then
11587                         set_dir_limits 0 0
11588                         echo "return code $rc received as expected"
11589
11590                         createmany -o $DIR/$tdir/file_extra_$nfiles. 5 ||
11591                                 error_exit "create failed w/o dir size limit"
11592
11593                         check_mds_dmesg '"has reached"' ||
11594                                 error_exit "reached message should be output"
11595
11596                         [ $has_warning = "false" ] &&
11597                                 error_exit "warning message should be output"
11598
11599                         dirsize=$(stat -c%s "$DIR/$tdir")
11600
11601                         [[ $dirsize -ge $maxsize ]] && return 0
11602                         error_exit "current dir size $dirsize, " \
11603                                    "previous limit $maxsize"
11604                 elif [ $rc -ne 0 ]; then
11605                         set_dir_limits 0 0
11606                         error_exit "return $rc received instead of expected " \
11607                                    "$EFBIG or $ENOSPC, files in dir $dirsize"
11608                 fi
11609                 nfiles=$((nfiles + 1))
11610                 dirsize=$(stat -c%s "$DIR/$tdir")
11611         done
11612
11613         set_dir_limits 0 0
11614         error "exceeded dir size limit $maxsize($MDSCOUNT) : $dirsize bytes"
11615 }
11616 run_test 129 "test directory size limit ========================"
11617
11618 OLDIFS="$IFS"
11619 cleanup_130() {
11620         trap 0
11621         IFS="$OLDIFS"
11622 }
11623
11624 test_130a() {
11625         local filefrag_op=$(filefrag -e 2>&1 | grep "invalid option")
11626         [ -n "$filefrag_op" ] && skip_env "filefrag does not support FIEMAP"
11627
11628         trap cleanup_130 EXIT RETURN
11629
11630         local fm_file=$DIR/$tfile
11631         $LFS setstripe -S 65536 -c 1 $fm_file || error "setstripe on $fm_file"
11632         dd if=/dev/zero of=$fm_file bs=65536 count=1 ||
11633                 error "dd failed for $fm_file"
11634
11635         # LU-1795: test filefrag/FIEMAP once, even if unsupported
11636         filefrag -ves $fm_file
11637         RC=$?
11638         [ "$(facet_fstype ost$(($($LFS getstripe -i $fm_file) + 1)))" = "zfs" ] &&
11639                 skip_env "ORI-366/LU-1941: FIEMAP unimplemented on ZFS"
11640         [ $RC != 0 ] && error "filefrag $fm_file failed"
11641
11642         filefrag_op=$(filefrag -ve -k $fm_file |
11643                         sed -n '/ext:/,/found/{/ext:/d; /found/d; p}')
11644         lun=$($LFS getstripe -i $fm_file)
11645
11646         start_blk=`echo $filefrag_op | cut -d: -f2 | cut -d. -f1`
11647         IFS=$'\n'
11648         tot_len=0
11649         for line in $filefrag_op
11650         do
11651                 frag_lun=`echo $line | cut -d: -f5`
11652                 ext_len=`echo $line | cut -d: -f4`
11653                 if (( $frag_lun != $lun )); then
11654                         cleanup_130
11655                         error "FIEMAP on 1-stripe file($fm_file) failed"
11656                         return
11657                 fi
11658                 (( tot_len += ext_len ))
11659         done
11660
11661         if (( lun != frag_lun || start_blk != 0 || tot_len != 64 )); then
11662                 cleanup_130
11663                 error "FIEMAP on 1-stripe file($fm_file) failed;"
11664                 return
11665         fi
11666
11667         cleanup_130
11668
11669         echo "FIEMAP on single striped file succeeded"
11670 }
11671 run_test 130a "FIEMAP (1-stripe file)"
11672
11673 test_130b() {
11674         [ "$OSTCOUNT" -lt "2" ] && skip_env "needs >= 2 OSTs"
11675
11676         local filefrag_op=$(filefrag -e 2>&1 | grep "invalid option")
11677         [ -n "$filefrag_op" ] && skip_env "filefrag does not support FIEMAP"
11678
11679         trap cleanup_130 EXIT RETURN
11680
11681         local fm_file=$DIR/$tfile
11682         $LFS setstripe -S 65536 -c $OSTCOUNT $fm_file ||
11683                         error "setstripe on $fm_file"
11684         [ "$(facet_fstype ost$(($($LFS getstripe -i $fm_file) + 1)))" = "zfs" ] &&
11685                 skip_env "ORI-366/LU-1941: FIEMAP unimplemented on ZFS"
11686
11687         dd if=/dev/zero of=$fm_file bs=1M count=$OSTCOUNT ||
11688                 error "dd failed on $fm_file"
11689
11690         filefrag -ves $fm_file || error "filefrag $fm_file failed"
11691         filefrag_op=$(filefrag -ve -k $fm_file |
11692                         sed -n '/ext:/,/found/{/ext:/d; /found/d; p}')
11693
11694         last_lun=$(echo $filefrag_op | cut -d: -f5 |
11695                 sed -e 's/^[ \t]*/0x/' | sed -e 's/0x0x/0x/')
11696
11697         IFS=$'\n'
11698         tot_len=0
11699         num_luns=1
11700         for line in $filefrag_op
11701         do
11702                 frag_lun=$(echo $line | cut -d: -f5 |
11703                         sed -e 's/^[ \t]*/0x/' | sed -e 's/0x0x/0x/')
11704                 ext_len=$(echo $line | cut -d: -f4)
11705                 if (( $frag_lun != $last_lun )); then
11706                         if (( tot_len != 1024 )); then
11707                                 cleanup_130
11708                                 error "FIEMAP on $fm_file failed; returned " \
11709                                 "len $tot_len for OST $last_lun instead of 1024"
11710                                 return
11711                         else
11712                                 (( num_luns += 1 ))
11713                                 tot_len=0
11714                         fi
11715                 fi
11716                 (( tot_len += ext_len ))
11717                 last_lun=$frag_lun
11718         done
11719         if (( num_luns != $OSTCOUNT || tot_len != 1024 )); then
11720                 cleanup_130
11721                 error "FIEMAP on $fm_file failed; returned wrong number of " \
11722                         "luns or wrong len for OST $last_lun"
11723                 return
11724         fi
11725
11726         cleanup_130
11727
11728         echo "FIEMAP on $OSTCOUNT-stripe file succeeded"
11729 }
11730 run_test 130b "FIEMAP ($OSTCOUNT-stripe file)"
11731
11732 test_130c() {
11733         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
11734
11735         filefrag_op=$(filefrag -e 2>&1 | grep "invalid option")
11736         [ -n "$filefrag_op" ] && skip "filefrag does not support FIEMAP"
11737
11738         trap cleanup_130 EXIT RETURN
11739
11740         local fm_file=$DIR/$tfile
11741         $LFS setstripe -S 65536 -c 2 $fm_file || error "setstripe on $fm_file"
11742         [ "$(facet_fstype ost$(($($LFS getstripe -i $fm_file) + 1)))" = "zfs" ] &&
11743                 skip_env "ORI-366/LU-1941: FIEMAP unimplemented on ZFS"
11744
11745         dd if=/dev/zero of=$fm_file seek=1 bs=1M count=1 ||
11746                         error "dd failed on $fm_file"
11747
11748         filefrag -ves $fm_file || error "filefrag $fm_file failed"
11749         filefrag_op=$(filefrag -ve -k $fm_file |
11750                 sed -n '/ext:/,/found/{/ext:/d; /found/d; p}')
11751
11752         last_lun=$(echo $filefrag_op | cut -d: -f5 |
11753                 sed -e 's/^[ \t]*/0x/' | sed -e 's/0x0x/0x/')
11754
11755         IFS=$'\n'
11756         tot_len=0
11757         num_luns=1
11758         for line in $filefrag_op
11759         do
11760                 frag_lun=$(echo $line | cut -d: -f5 |
11761                         sed -e 's/^[ \t]*/0x/' | sed -e 's/0x0x/0x/')
11762                 ext_len=$(echo $line | cut -d: -f4)
11763                 if (( $frag_lun != $last_lun )); then
11764                         logical=`echo $line | cut -d: -f2 | cut -d. -f1`
11765                         if (( logical != 512 )); then
11766                                 cleanup_130
11767                                 error "FIEMAP on $fm_file failed; returned " \
11768                                 "logical start for lun $logical instead of 512"
11769                                 return
11770                         fi
11771                         if (( tot_len != 512 )); then
11772                                 cleanup_130
11773                                 error "FIEMAP on $fm_file failed; returned " \
11774                                 "len $tot_len for OST $last_lun instead of 1024"
11775                                 return
11776                         else
11777                                 (( num_luns += 1 ))
11778                                 tot_len=0
11779                         fi
11780                 fi
11781                 (( tot_len += ext_len ))
11782                 last_lun=$frag_lun
11783         done
11784         if (( num_luns != 2 || tot_len != 512 )); then
11785                 cleanup_130
11786                 error "FIEMAP on $fm_file failed; returned wrong number of " \
11787                         "luns or wrong len for OST $last_lun"
11788                 return
11789         fi
11790
11791         cleanup_130
11792
11793         echo "FIEMAP on 2-stripe file with hole succeeded"
11794 }
11795 run_test 130c "FIEMAP (2-stripe file with hole)"
11796
11797 test_130d() {
11798         [[ $OSTCOUNT -lt 3 ]] && skip_env "needs >= 3 OSTs"
11799
11800         filefrag_op=$(filefrag -e 2>&1 | grep "invalid option")
11801         [ -n "$filefrag_op" ] && skip "filefrag does not support FIEMAP"
11802
11803         trap cleanup_130 EXIT RETURN
11804
11805         local fm_file=$DIR/$tfile
11806         $LFS setstripe -S 65536 -c $OSTCOUNT $fm_file ||
11807                         error "setstripe on $fm_file"
11808         [ "$(facet_fstype ost$(($($LFS getstripe -i $fm_file) + 1)))" = "zfs" ] &&
11809                 skip_env "ORI-366/LU-1941: FIEMAP unimplemented on ZFS"
11810
11811         local actual_stripe_count=$($LFS getstripe -c $fm_file)
11812         dd if=/dev/zero of=$fm_file bs=1M count=$actual_stripe_count ||
11813                 error "dd failed on $fm_file"
11814
11815         filefrag -ves $fm_file || error "filefrag $fm_file failed"
11816         filefrag_op=$(filefrag -ve -k $fm_file |
11817                         sed -n '/ext:/,/found/{/ext:/d; /found/d; p}')
11818
11819         last_lun=$(echo $filefrag_op | cut -d: -f5 |
11820                 sed -e 's/^[ \t]*/0x/' | sed -e 's/0x0x/0x/')
11821
11822         IFS=$'\n'
11823         tot_len=0
11824         num_luns=1
11825         for line in $filefrag_op
11826         do
11827                 frag_lun=$(echo $line | cut -d: -f5 |
11828                         sed -e 's/^[ \t]*/0x/' | sed -e 's/0x0x/0x/')
11829                 ext_len=$(echo $line | cut -d: -f4)
11830                 if (( $frag_lun != $last_lun )); then
11831                         if (( tot_len != 1024 )); then
11832                                 cleanup_130
11833                                 error "FIEMAP on $fm_file failed; returned " \
11834                                 "len $tot_len for OST $last_lun instead of 1024"
11835                                 return
11836                         else
11837                                 (( num_luns += 1 ))
11838                                 tot_len=0
11839                         fi
11840                 fi
11841                 (( tot_len += ext_len ))
11842                 last_lun=$frag_lun
11843         done
11844         if (( num_luns != actual_stripe_count || tot_len != 1024 )); then
11845                 cleanup_130
11846                 error "FIEMAP on $fm_file failed; returned wrong number of " \
11847                         "luns or wrong len for OST $last_lun"
11848                 return
11849         fi
11850
11851         cleanup_130
11852
11853         echo "FIEMAP on N-stripe file succeeded"
11854 }
11855 run_test 130d "FIEMAP (N-stripe file)"
11856
11857 test_130e() {
11858         [[ $OSTCOUNT -lt 2 ]] && skip_env "needs >= 2 OSTs"
11859
11860         filefrag_op=$(filefrag -e 2>&1 | grep "invalid option")
11861         [ -n "$filefrag_op" ] && skip_env "filefrag does not support FIEMAP"
11862
11863         trap cleanup_130 EXIT RETURN
11864
11865         local fm_file=$DIR/$tfile
11866         $LFS setstripe -S 131072 -c 2 $fm_file || error "setstripe on $fm_file"
11867         [ "$(facet_fstype ost$(($($LFS getstripe -i $fm_file) + 1)))" = "zfs" ] &&
11868                 skip_env "ORI-366/LU-1941: FIEMAP unimplemented on ZFS"
11869
11870         NUM_BLKS=512
11871         EXPECTED_LEN=$(( (NUM_BLKS / 2) * 64 ))
11872         for ((i = 0; i < $NUM_BLKS; i++))
11873         do
11874                 dd if=/dev/zero of=$fm_file count=1 bs=64k seek=$((2*$i)) conv=notrunc > /dev/null 2>&1
11875         done
11876
11877         filefrag -ves $fm_file || error "filefrag $fm_file failed"
11878         filefrag_op=$(filefrag -ve -k $fm_file |
11879                         sed -n '/ext:/,/found/{/ext:/d; /found/d; p}')
11880
11881         last_lun=$(echo $filefrag_op | cut -d: -f5 |
11882                 sed -e 's/^[ \t]*/0x/' | sed -e 's/0x0x/0x/')
11883
11884         IFS=$'\n'
11885         tot_len=0
11886         num_luns=1
11887         for line in $filefrag_op
11888         do
11889                 frag_lun=$(echo $line | cut -d: -f5 |
11890                         sed -e 's/^[ \t]*/0x/' | sed -e 's/0x0x/0x/')
11891                 ext_len=$(echo $line | cut -d: -f4)
11892                 if (( $frag_lun != $last_lun )); then
11893                         if (( tot_len != $EXPECTED_LEN )); then
11894                                 cleanup_130
11895                                 error "FIEMAP on $fm_file failed; returned " \
11896                                 "len $tot_len for OST $last_lun instead " \
11897                                 "of $EXPECTED_LEN"
11898                                 return
11899                         else
11900                                 (( num_luns += 1 ))
11901                                 tot_len=0
11902                         fi
11903                 fi
11904                 (( tot_len += ext_len ))
11905                 last_lun=$frag_lun
11906         done
11907         if (( num_luns != 2 || tot_len != $EXPECTED_LEN )); then
11908                 cleanup_130
11909                 error "FIEMAP on $fm_file failed; returned wrong number " \
11910                         "of luns or wrong len for OST $last_lun"
11911                 return
11912         fi
11913
11914         cleanup_130
11915
11916         echo "FIEMAP with continuation calls succeeded"
11917 }
11918 run_test 130e "FIEMAP (test continuation FIEMAP calls)"
11919
11920 test_130f() {
11921         filefrag_op=$(filefrag -e 2>&1 | grep "invalid option")
11922         [ -n "$filefrag_op" ] && skip "filefrag does not support FIEMAP"
11923
11924         local fm_file=$DIR/$tfile
11925         $MULTIOP $fm_file oO_RDWR:O_CREAT:O_LOV_DELAY_CREATE:T33554432c ||
11926                 error "multiop create with lov_delay_create on $fm_file"
11927
11928         filefrag -ves $fm_file || error "filefrag $fm_file failed"
11929         filefrag_extents=$(filefrag -vek $fm_file |
11930                            awk '/extents? found/ { print $2 }')
11931         if [[ "$filefrag_extents" != "0" ]]; then
11932                 error "FIEMAP on $fm_file failed; " \
11933                       "returned $filefrag_extents expected 0"
11934         fi
11935
11936         rm -f $fm_file
11937 }
11938 run_test 130f "FIEMAP (unstriped file)"
11939
11940 # Test for writev/readv
11941 test_131a() {
11942         rwv -f $DIR/$tfile -w -n 3 524288 1048576 1572864 ||
11943                 error "writev test failed"
11944         rwv -f $DIR/$tfile -r -v -n 2 1572864 1048576 ||
11945                 error "readv failed"
11946         rm -f $DIR/$tfile
11947 }
11948 run_test 131a "test iov's crossing stripe boundary for writev/readv"
11949
11950 test_131b() {
11951         local fsize=$((524288 + 1048576 + 1572864))
11952         rwv -f $DIR/$tfile -w -a -n 3 524288 1048576 1572864 &&
11953                 $CHECKSTAT -t file $DIR/$tfile -s $fsize ||
11954                         error "append writev test failed"
11955
11956         ((fsize += 1572864 + 1048576))
11957         rwv -f $DIR/$tfile -w -a -n 2 1572864 1048576 &&
11958                 $CHECKSTAT -t file $DIR/$tfile -s $fsize ||
11959                         error "append writev test failed"
11960         rm -f $DIR/$tfile
11961 }
11962 run_test 131b "test append writev"
11963
11964 test_131c() {
11965         rwv -f $DIR/$tfile -w -d -n 1 1048576 || return 0
11966         error "NOT PASS"
11967 }
11968 run_test 131c "test read/write on file w/o objects"
11969
11970 test_131d() {
11971         rwv -f $DIR/$tfile -w -n 1 1572864
11972         NOB=`rwv -f $DIR/$tfile -r -n 3 524288 524288 1048576 | awk '/error/ {print $6}'`
11973         if [ "$NOB" != 1572864 ]; then
11974                 error "Short read filed: read $NOB bytes instead of 1572864"
11975         fi
11976         rm -f $DIR/$tfile
11977 }
11978 run_test 131d "test short read"
11979
11980 test_131e() {
11981         rwv -f $DIR/$tfile -w -s 1048576 -n 1 1048576
11982         rwv -f $DIR/$tfile -r -z -s 0 -n 1 524288 || \
11983         error "read hitting hole failed"
11984         rm -f $DIR/$tfile
11985 }
11986 run_test 131e "test read hitting hole"
11987
11988 check_stats() {
11989         local facet=$1
11990         local op=$2
11991         local want=${3:-0}
11992         local res
11993
11994         case $facet in
11995         mds*) res=$(do_facet $facet \
11996                    $LCTL get_param mdt.$FSNAME-MDT0000.md_stats | grep "$op")
11997                  ;;
11998         ost*) res=$(do_facet $facet \
11999                    $LCTL get_param obdfilter.$FSNAME-OST0000.stats | grep "$op")
12000                  ;;
12001         *) error "Wrong facet '$facet'" ;;
12002         esac
12003         [ "$res" ] || error "The counter for $op on $facet was not incremented"
12004         # if the argument $3 is zero, it means any stat increment is ok.
12005         if [[ $want -gt 0 ]]; then
12006                 local count=$(echo $res | awk '{ print $2 }')
12007                 [[ $count -ne $want ]] &&
12008                         error "The $op counter on $facet is $count, not $want"
12009         fi
12010 }
12011
12012 test_133a() {
12013         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12014         remote_ost_nodsh && skip "remote OST with nodsh"
12015         remote_mds_nodsh && skip "remote MDS with nodsh"
12016         do_facet $SINGLEMDS $LCTL list_param mdt.*.rename_stats ||
12017                 skip_env "MDS doesn't support rename stats"
12018
12019         local testdir=$DIR/${tdir}/stats_testdir
12020
12021         mkdir -p $DIR/${tdir}
12022
12023         # clear stats.
12024         do_facet $SINGLEMDS $LCTL set_param mdt.*.md_stats=clear
12025         do_facet ost1 $LCTL set_param obdfilter.*.stats=clear
12026
12027         # verify mdt stats first.
12028         mkdir ${testdir} || error "mkdir failed"
12029         check_stats $SINGLEMDS "mkdir" 1
12030         touch ${testdir}/${tfile} || error "touch failed"
12031         check_stats $SINGLEMDS "open" 1
12032         check_stats $SINGLEMDS "close" 1
12033         [ $MDS1_VERSION -ge $(version_code 2.8.54) ] && {
12034                 mknod ${testdir}/${tfile}-pipe p || error "mknod failed"
12035                 check_stats $SINGLEMDS "mknod" 2
12036         }
12037         rm -f ${testdir}/${tfile}-pipe || error "pipe remove failed"
12038         check_stats $SINGLEMDS "unlink" 1
12039         rm -f ${testdir}/${tfile} || error "file remove failed"
12040         check_stats $SINGLEMDS "unlink" 2
12041
12042         # remove working dir and check mdt stats again.
12043         rmdir ${testdir} || error "rmdir failed"
12044         check_stats $SINGLEMDS "rmdir" 1
12045
12046         local testdir1=$DIR/${tdir}/stats_testdir1
12047         mkdir -p ${testdir}
12048         mkdir -p ${testdir1}
12049         touch ${testdir1}/test1
12050         mv ${testdir1}/test1 ${testdir} || error "file crossdir rename"
12051         check_stats $SINGLEMDS "crossdir_rename" 1
12052
12053         mv ${testdir}/test1 ${testdir}/test0 || error "file samedir rename"
12054         check_stats $SINGLEMDS "samedir_rename" 1
12055
12056         rm -rf $DIR/${tdir}
12057 }
12058 run_test 133a "Verifying MDT stats ========================================"
12059
12060 test_133b() {
12061         local res
12062
12063         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12064         remote_ost_nodsh && skip "remote OST with nodsh"
12065         remote_mds_nodsh && skip "remote MDS with nodsh"
12066
12067         local testdir=$DIR/${tdir}/stats_testdir
12068
12069         mkdir -p ${testdir} || error "mkdir failed"
12070         touch ${testdir}/${tfile} || error "touch failed"
12071         cancel_lru_locks mdc
12072
12073         # clear stats.
12074         do_facet $SINGLEMDS $LCTL set_param mdt.*.md_stats=clear
12075         do_facet ost1 $LCTL set_param obdfilter.*.stats=clear
12076
12077         # extra mdt stats verification.
12078         chmod 444 ${testdir}/${tfile} || error "chmod failed"
12079         check_stats $SINGLEMDS "setattr" 1
12080         do_facet $SINGLEMDS $LCTL set_param mdt.*.md_stats=clear
12081         if [ $MDS1_VERSION -ne $(version_code 2.2.0) ]
12082         then            # LU-1740
12083                 ls -l ${testdir}/${tfile} > /dev/null|| error "ls failed"
12084                 check_stats $SINGLEMDS "getattr" 1
12085         fi
12086         rm -rf $DIR/${tdir}
12087
12088         # when DNE is enabled, MDT uses STATFS RPC to ping other targets
12089         # so the check below is not reliable
12090         [ $MDSCOUNT -eq 1 ] || return 0
12091
12092         # Sleep to avoid a cached response.
12093         #define OBD_STATFS_CACHE_SECONDS 1
12094         sleep 2
12095         do_facet $SINGLEMDS $LCTL set_param mdt.*.md_stats=clear
12096         do_facet ost1 $LCTL set_param obdfilter.*.exports.*.stats=clear
12097         $LFS df || error "lfs failed"
12098         check_stats $SINGLEMDS "statfs" 1
12099
12100         # check aggregated statfs (LU-10018)
12101         [ $MDS1_VERSION -lt $(version_code 2.11.54) ] &&
12102                 return 0
12103         [ $CLIENT_VERSION -lt $(version_code 2.11.54) ] &&
12104                 return 0
12105         sleep 2
12106         do_facet $SINGLEMDS $LCTL set_param mdt.*.md_stats=clear
12107         do_facet ost1 $LCTL set_param obdfilter.*.exports.*.stats=clear
12108         df $DIR
12109         check_stats $SINGLEMDS "statfs" 1
12110
12111         # We want to check that the client didn't send OST_STATFS to
12112         # ost1 but the MDT also uses OST_STATFS for precreate. So some
12113         # extra care is needed here.
12114         if remote_mds; then
12115                 local nid=$($LCTL list_nids | head -1 | sed  "s/\./\\\./g")
12116                 local param="obdfilter.$FSNAME-OST0000.exports.'$nid'.stats"
12117
12118                 res=$(do_facet ost1 $LCTL get_param $param | grep statfs)
12119                 [ "$res" ] && error "OST got STATFS"
12120         fi
12121
12122         return 0
12123 }
12124 run_test 133b "Verifying extra MDT stats =================================="
12125
12126 test_133c() {
12127         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12128         remote_ost_nodsh && skip "remote OST with nodsh"
12129         remote_mds_nodsh && skip "remote MDS with nodsh"
12130
12131         local testdir=$DIR/$tdir/stats_testdir
12132
12133         test_mkdir -p $testdir
12134
12135         # verify obdfilter stats.
12136         $LFS setstripe -c 1 -i 0 $testdir/$tfile
12137         sync
12138         cancel_lru_locks osc
12139         wait_delete_completed
12140
12141         # clear stats.
12142         do_facet $SINGLEMDS $LCTL set_param mdt.*.md_stats=clear
12143         do_facet ost1 $LCTL set_param obdfilter.*.stats=clear
12144
12145         dd if=/dev/zero of=$testdir/$tfile conv=notrunc bs=512k count=1 ||
12146                 error "dd failed"
12147         sync
12148         cancel_lru_locks osc
12149         check_stats ost1 "write" 1
12150
12151         dd if=$testdir/$tfile of=/dev/null bs=1k count=1 || error "dd failed"
12152         check_stats ost1 "read" 1
12153
12154         > $testdir/$tfile || error "truncate failed"
12155         check_stats ost1 "punch" 1
12156
12157         rm -f $testdir/$tfile || error "file remove failed"
12158         wait_delete_completed
12159         check_stats ost1 "destroy" 1
12160
12161         rm -rf $DIR/$tdir
12162 }
12163 run_test 133c "Verifying OST stats ========================================"
12164
12165 order_2() {
12166         local value=$1
12167         local orig=$value
12168         local order=1
12169
12170         while [ $value -ge 2 ]; do
12171                 order=$((order*2))
12172                 value=$((value/2))
12173         done
12174
12175         if [ $orig -gt $order ]; then
12176                 order=$((order*2))
12177         fi
12178         echo $order
12179 }
12180
12181 size_in_KMGT() {
12182     local value=$1
12183     local size=('K' 'M' 'G' 'T');
12184     local i=0
12185     local size_string=$value
12186
12187     while [ $value -ge 1024 ]; do
12188         if [ $i -gt 3 ]; then
12189             #T is the biggest unit we get here, if that is bigger,
12190             #just return XXXT
12191             size_string=${value}T
12192             break
12193         fi
12194         value=$((value >> 10))
12195         if [ $value -lt 1024 ]; then
12196             size_string=${value}${size[$i]}
12197             break
12198         fi
12199         i=$((i + 1))
12200     done
12201
12202     echo $size_string
12203 }
12204
12205 get_rename_size() {
12206         local size=$1
12207         local context=${2:-.}
12208         local sample=$(do_facet $SINGLEMDS $LCTL \
12209                 get_param mdt.$FSNAME-MDT0000.rename_stats |
12210                 grep -A1 $context |
12211                 awk '/ '${size}'/ {print $4}' | sed -e "s/,//g")
12212         echo $sample
12213 }
12214
12215 test_133d() {
12216         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12217         remote_ost_nodsh && skip "remote OST with nodsh"
12218         remote_mds_nodsh && skip "remote MDS with nodsh"
12219         do_facet $SINGLEMDS $LCTL list_param mdt.*.rename_stats ||
12220                 skip_env "MDS doesn't support rename stats"
12221
12222         local testdir1=$DIR/${tdir}/stats_testdir1
12223         local testdir2=$DIR/${tdir}/stats_testdir2
12224         mkdir -p $DIR/${tdir}
12225
12226         do_facet $SINGLEMDS $LCTL set_param mdt.*.rename_stats=clear
12227
12228         lfs mkdir -i 0 -c 1 ${testdir1} || error "mkdir failed"
12229         lfs mkdir -i 0 -c 1 ${testdir2} || error "mkdir failed"
12230
12231         createmany -o $testdir1/test 512 || error "createmany failed"
12232
12233         # check samedir rename size
12234         mv ${testdir1}/test0 ${testdir1}/test_0
12235
12236         local testdir1_size=$(ls -l $DIR/${tdir} |
12237                 awk '/stats_testdir1/ {print $5}')
12238         local testdir2_size=$(ls -l $DIR/${tdir} |
12239                 awk '/stats_testdir2/ {print $5}')
12240
12241         testdir1_size=$(order_2 $testdir1_size)
12242         testdir2_size=$(order_2 $testdir2_size)
12243
12244         testdir1_size=$(size_in_KMGT $testdir1_size)
12245         testdir2_size=$(size_in_KMGT $testdir2_size)
12246
12247         echo "source rename dir size: ${testdir1_size}"
12248         echo "target rename dir size: ${testdir2_size}"
12249
12250         local cmd="do_facet $SINGLEMDS $LCTL "
12251         cmd+="get_param mdt.$FSNAME-MDT0000.rename_stats"
12252
12253         eval $cmd || error "$cmd failed"
12254         local samedir=$($cmd | grep 'same_dir')
12255         local same_sample=$(get_rename_size $testdir1_size)
12256         [ -z "$samedir" ] && error "samedir_rename_size count error"
12257         [[ $same_sample -eq 1 ]] ||
12258                 error "samedir_rename_size error $same_sample"
12259         echo "Check same dir rename stats success"
12260
12261         do_facet $SINGLEMDS $LCTL set_param mdt.*.rename_stats=clear
12262
12263         # check crossdir rename size
12264         mv ${testdir1}/test_0 ${testdir2}/test_0
12265
12266         testdir1_size=$(ls -l $DIR/${tdir} |
12267                 awk '/stats_testdir1/ {print $5}')
12268         testdir2_size=$(ls -l $DIR/${tdir} |
12269                 awk '/stats_testdir2/ {print $5}')
12270
12271         testdir1_size=$(order_2 $testdir1_size)
12272         testdir2_size=$(order_2 $testdir2_size)
12273
12274         testdir1_size=$(size_in_KMGT $testdir1_size)
12275         testdir2_size=$(size_in_KMGT $testdir2_size)
12276
12277         echo "source rename dir size: ${testdir1_size}"
12278         echo "target rename dir size: ${testdir2_size}"
12279
12280         eval $cmd || error "$cmd failed"
12281         local crossdir=$($cmd | grep 'crossdir')
12282         local src_sample=$(get_rename_size $testdir1_size crossdir_src)
12283         local tgt_sample=$(get_rename_size $testdir2_size crossdir_tgt)
12284         [ -z "$crossdir" ] && error "crossdir_rename_size count error"
12285         [[ $src_sample -eq 1 ]] ||
12286                 error "crossdir_rename_size error $src_sample"
12287         [[ $tgt_sample -eq 1 ]] ||
12288                 error "crossdir_rename_size error $tgt_sample"
12289         echo "Check cross dir rename stats success"
12290         rm -rf $DIR/${tdir}
12291 }
12292 run_test 133d "Verifying rename_stats ========================================"
12293
12294 test_133e() {
12295         remote_mds_nodsh && skip "remote MDS with nodsh"
12296         remote_ost_nodsh && skip "remote OST with nodsh"
12297         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12298
12299         local testdir=$DIR/${tdir}/stats_testdir
12300         local ctr f0 f1 bs=32768 count=42 sum
12301
12302         mkdir -p ${testdir} || error "mkdir failed"
12303
12304         $LFS setstripe -c 1 -i 0 ${testdir}/${tfile}
12305
12306         for ctr in {write,read}_bytes; do
12307                 sync
12308                 cancel_lru_locks osc
12309
12310                 do_facet ost1 $LCTL set_param -n \
12311                         "obdfilter.*.exports.clear=clear"
12312
12313                 if [ $ctr = write_bytes ]; then
12314                         f0=/dev/zero
12315                         f1=${testdir}/${tfile}
12316                 else
12317                         f0=${testdir}/${tfile}
12318                         f1=/dev/null
12319                 fi
12320
12321                 dd if=$f0 of=$f1 conv=notrunc bs=$bs count=$count || \
12322                         error "dd failed"
12323                 sync
12324                 cancel_lru_locks osc
12325
12326                 sum=$(do_facet ost1 $LCTL get_param \
12327                         "obdfilter.*.exports.*.stats" |
12328                         awk -v ctr=$ctr 'BEGIN { sum = 0 }
12329                                 $1 == ctr { sum += $7 }
12330                                 END { printf("%0.0f", sum) }')
12331
12332                 if ((sum != bs * count)); then
12333                         error "Bad $ctr sum, expected $((bs * count)), got $sum"
12334                 fi
12335         done
12336
12337         rm -rf $DIR/${tdir}
12338 }
12339 run_test 133e "Verifying OST {read,write}_bytes nid stats ================="
12340
12341 proc_regexp="/{proc,sys}/{fs,sys,kernel/debug}/{lustre,lnet}/"
12342
12343 # Some versions of find (4.5.11, 4.5.14) included in CentOS 7.3-7.5 do
12344 # not honor the -ignore_readdir_race option correctly. So we call
12345 # error_ignore() rather than error() in these cases. See LU-11152.
12346 error_133() {
12347         if (find --version; do_facet mds1 find --version) |
12348                 grep -q '\b4\.5\.1[1-4]\b'; then
12349                 error_ignore LU-11152 "$@"
12350         else
12351                 error "$@"
12352         fi
12353 }
12354
12355 test_133f() {
12356         # First without trusting modes.
12357         local proc_dirs=$(eval \ls -d $proc_regexp 2>/dev/null)
12358         echo "proc_dirs='$proc_dirs'"
12359         [ -n "$proc_dirs" ] || error "no proc_dirs on $HOSTNAME"
12360         find $proc_dirs -exec cat '{}' \; &> /dev/null
12361
12362         # Second verifying readability.
12363         $LCTL get_param -R '*' &> /dev/null
12364
12365         # Verifing writability with badarea_io.
12366         find $proc_dirs \
12367                 -ignore_readdir_race \
12368                 -type f \
12369                 -not -name force_lbug \
12370                 -not -name changelog_mask \
12371                 -exec badarea_io '{}' \; ||
12372                         error_133 "find $proc_dirs failed"
12373 }
12374 run_test 133f "Check reads/writes of client lustre proc files with bad area io"
12375
12376 test_133g() {
12377         remote_mds_nodsh && skip "remote MDS with nodsh"
12378         remote_ost_nodsh && skip "remote OST with nodsh"
12379
12380         # eventually, this can also be replaced with "lctl get_param -R",
12381         # but not until that option is always available on the server
12382         local facet
12383         for facet in mds1 ost1; do
12384                 [ $(lustre_version_code $facet) -le $(version_code 2.5.54) ] &&
12385                         skip_noexit "Too old lustre on $facet"
12386                 local facet_proc_dirs=$(do_facet $facet \
12387                                         \\\ls -d $proc_regexp 2>/dev/null)
12388                 echo "${facet}_proc_dirs='$facet_proc_dirs'"
12389                 [ -z "$facet_proc_dirs" ] && error "no proc_dirs on $facet"
12390                 do_facet $facet find $facet_proc_dirs \
12391                         ! -name req_history \
12392                         -exec cat '{}' \\\; &> /dev/null
12393
12394                 do_facet $facet find $facet_proc_dirs \
12395                         ! -name req_history \
12396                         -type f \
12397                         -exec cat '{}' \\\; &> /dev/null ||
12398                                 error "proc file read failed"
12399
12400                 do_facet $facet find $facet_proc_dirs \
12401                         -ignore_readdir_race \
12402                         -type f \
12403                         -not -name force_lbug \
12404                         -not -name changelog_mask \
12405                         -exec badarea_io '{}' \\\; ||
12406                                 error_133 "$facet find $facet_proc_dirs failed"
12407         done
12408
12409         # remount the FS in case writes/reads /proc break the FS
12410         cleanup || error "failed to unmount"
12411         setup || error "failed to setup"
12412         true
12413 }
12414 run_test 133g "Check reads/writes of server lustre proc files with bad area io"
12415
12416 test_133h() {
12417         remote_mds_nodsh && skip "remote MDS with nodsh"
12418         remote_ost_nodsh && skip "remote OST with nodsh"
12419         [[ $MDS1_VERSION -lt $(version_code 2.9.54) ]] &&
12420                 skip "Need MDS version at least 2.9.54"
12421
12422         local facet
12423
12424         for facet in client mds1 ost1; do
12425                 local facet_proc_dirs=$(do_facet $facet \
12426                                         \\\ls -d $proc_regexp 2> /dev/null)
12427                 [ -z "$facet_proc_dirs" ] && error "no proc_dirs on $facet"
12428                 echo "${facet}_proc_dirs='$facet_proc_dirs'"
12429                 # Get the list of files that are missing the terminating newline
12430                 local missing=($(do_facet $facet \
12431                         find ${facet_proc_dirs} -type f \|              \
12432                                 while read F\; do                       \
12433                                         awk -v FS='\v' -v RS='\v\v'     \
12434                                         "'END { if(NR>0 &&              \
12435                                         \\\$NF !~ /.*\\\n\$/)           \
12436                                                 print FILENAME}'"       \
12437                                         '\$F'\;                         \
12438                                 done 2>/dev/null))
12439                 [ ${#missing[*]} -eq 0 ] ||
12440                         error "files do not end with newline: ${missing[*]}"
12441         done
12442 }
12443 run_test 133h "Proc files should end with newlines"
12444
12445 test_134a() {
12446         remote_mds_nodsh && skip "remote MDS with nodsh"
12447         [[ $MDS1_VERSION -lt $(version_code 2.7.54) ]] &&
12448                 skip "Need MDS version at least 2.7.54"
12449
12450         mkdir -p $DIR/$tdir || error "failed to create $DIR/$tdir"
12451         cancel_lru_locks mdc
12452
12453         local nsdir="ldlm.namespaces.*-MDT0000-mdc-*"
12454         local unused=$($LCTL get_param -n $nsdir.lock_unused_count)
12455         [ $unused -eq 0 ] || error "$unused locks are not cleared"
12456
12457         local nr=1000
12458         createmany -o $DIR/$tdir/f $nr ||
12459                 error "failed to create $nr files in $DIR/$tdir"
12460         unused=$($LCTL get_param -n $nsdir.lock_unused_count)
12461
12462         #define OBD_FAIL_LDLM_WATERMARK_LOW     0x327
12463         do_facet mds1 $LCTL set_param fail_loc=0x327
12464         do_facet mds1 $LCTL set_param fail_val=500
12465         touch $DIR/$tdir/m
12466
12467         echo "sleep 10 seconds ..."
12468         sleep 10
12469         local lck_cnt=$($LCTL get_param -n $nsdir.lock_unused_count)
12470
12471         do_facet mds1 $LCTL set_param fail_loc=0
12472         do_facet mds1 $LCTL set_param fail_val=0
12473         [ $lck_cnt -lt $unused ] ||
12474                 error "No locks reclaimed, before:$unused, after:$lck_cnt"
12475
12476         rm $DIR/$tdir/m
12477         unlinkmany $DIR/$tdir/f $nr
12478 }
12479 run_test 134a "Server reclaims locks when reaching lock_reclaim_threshold"
12480
12481 test_134b() {
12482         remote_mds_nodsh && skip "remote MDS with nodsh"
12483         [[ $MDS1_VERSION -lt $(version_code 2.7.54) ]] &&
12484                 skip "Need MDS version at least 2.7.54"
12485
12486         mkdir -p $DIR/$tdir || error "failed to create $DIR/$tdir"
12487         cancel_lru_locks mdc
12488
12489         local low_wm=$(do_facet mds1 $LCTL get_param -n \
12490                         ldlm.lock_reclaim_threshold_mb)
12491         # disable reclaim temporarily
12492         do_facet mds1 $LCTL set_param ldlm.lock_reclaim_threshold_mb=0
12493
12494         #define OBD_FAIL_LDLM_WATERMARK_HIGH     0x328
12495         do_facet mds1 $LCTL set_param fail_loc=0x328
12496         do_facet mds1 $LCTL set_param fail_val=500
12497
12498         $LCTL set_param debug=+trace
12499
12500         local nr=600
12501         createmany -o $DIR/$tdir/f $nr &
12502         local create_pid=$!
12503
12504         echo "Sleep $TIMEOUT seconds ..."
12505         sleep $TIMEOUT
12506         if ! ps -p $create_pid  > /dev/null 2>&1; then
12507                 do_facet mds1 $LCTL set_param fail_loc=0
12508                 do_facet mds1 $LCTL set_param fail_val=0
12509                 do_facet mds1 $LCTL set_param \
12510                         ldlm.lock_reclaim_threshold_mb=${low_wm}m
12511                 error "createmany finished incorrectly!"
12512         fi
12513         do_facet mds1 $LCTL set_param fail_loc=0
12514         do_facet mds1 $LCTL set_param fail_val=0
12515         do_facet mds1 $LCTL set_param ldlm.lock_reclaim_threshold_mb=${low_wm}m
12516         wait $create_pid || return 1
12517
12518         unlinkmany $DIR/$tdir/f $nr
12519 }
12520 run_test 134b "Server rejects lock request when reaching lock_limit_mb"
12521
12522 test_140() { #bug-17379
12523         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12524
12525         test_mkdir $DIR/$tdir
12526         cd $DIR/$tdir || error "Changing to $DIR/$tdir"
12527         cp $(which stat) . || error "Copying stat to $DIR/$tdir"
12528
12529         # VFS limits max symlink depth to 5(4KSTACK) or 7(8KSTACK) or 8
12530         # For kernel > 3.5, bellow only tests consecutive symlink (MAX 40)
12531         local i=0
12532         while i=$((i + 1)); do
12533                 test_mkdir $i
12534                 cd $i || error "Changing to $i"
12535                 ln -s ../stat stat || error "Creating stat symlink"
12536                 # Read the symlink until ELOOP present,
12537                 # not LBUGing the system is considered success,
12538                 # we didn't overrun the stack.
12539                 $OPENFILE -f O_RDONLY stat >/dev/null 2>&1; ret=$?
12540                 if [ $ret -ne 0 ]; then
12541                         if [ $ret -eq 40 ]; then
12542                                 break  # -ELOOP
12543                         else
12544                                 error "Open stat symlink"
12545                                         return
12546                         fi
12547                 fi
12548         done
12549         i=$((i - 1))
12550         echo "The symlink depth = $i"
12551         [ $i -eq 5 ] || [ $i -eq 7 ] || [ $i -eq 8 ] || [ $i -eq 40 ] ||
12552                 error "Invalid symlink depth"
12553
12554         # Test recursive symlink
12555         ln -s symlink_self symlink_self
12556         $OPENFILE -f O_RDONLY symlink_self >/dev/null 2>&1; ret=$?
12557         echo "open symlink_self returns $ret"
12558         [ $ret -eq 40 ] || error "recursive symlink doesn't return -ELOOP"
12559 }
12560 run_test 140 "Check reasonable stack depth (shouldn't LBUG) ===="
12561
12562 test_150() {
12563         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12564
12565         local TF="$TMP/$tfile"
12566
12567         dd if=/dev/urandom of=$TF bs=6096 count=1 || error "dd failed"
12568         cp $TF $DIR/$tfile
12569         cancel_lru_locks $OSC
12570         cmp $TF $DIR/$tfile || error "$TMP/$tfile $DIR/$tfile differ"
12571         remount_client $MOUNT
12572         df -P $MOUNT
12573         cmp $TF $DIR/$tfile || error "$TF $DIR/$tfile differ (remount)"
12574
12575         $TRUNCATE $TF 6000
12576         $TRUNCATE $DIR/$tfile 6000
12577         cancel_lru_locks $OSC
12578         cmp $TF $DIR/$tfile || error "$TF $DIR/$tfile differ (truncate1)"
12579
12580         echo "12345" >>$TF
12581         echo "12345" >>$DIR/$tfile
12582         cancel_lru_locks $OSC
12583         cmp $TF $DIR/$tfile || error "$TF $DIR/$tfile differ (append1)"
12584
12585         echo "12345" >>$TF
12586         echo "12345" >>$DIR/$tfile
12587         cancel_lru_locks $OSC
12588         cmp $TF $DIR/$tfile || error "$TF $DIR/$tfile differ (append2)"
12589
12590         rm -f $TF
12591         true
12592 }
12593 run_test 150 "truncate/append tests"
12594
12595 #LU-2902 roc_hit was not able to read all values from lproc
12596 function roc_hit_init() {
12597         local list=$(comma_list $(osts_nodes))
12598         local dir=$DIR/$tdir-check
12599         local file=$dir/$tfile
12600         local BEFORE
12601         local AFTER
12602         local idx
12603
12604         test_mkdir $dir
12605         #use setstripe to do a write to every ost
12606         for i in $(seq 0 $((OSTCOUNT-1))); do
12607                 $LFS setstripe -c 1 -i $i $dir || error "$LFS setstripe $file failed"
12608                 dd if=/dev/urandom of=$file bs=4k count=4 2>&1 > /dev/null
12609                 idx=$(printf %04x $i)
12610                 BEFORE=$(get_osd_param $list *OST*$idx stats |
12611                         awk '$1 == "cache_access" {sum += $7}
12612                                 END { printf("%0.0f", sum) }')
12613
12614                 cancel_lru_locks osc
12615                 cat $file >/dev/null
12616
12617                 AFTER=$(get_osd_param $list *OST*$idx stats |
12618                         awk '$1 == "cache_access" {sum += $7}
12619                                 END { printf("%0.0f", sum) }')
12620
12621                 echo BEFORE:$BEFORE AFTER:$AFTER
12622                 if ! let "AFTER - BEFORE == 4"; then
12623                         rm -rf $dir
12624                         error "roc_hit is not safe to use"
12625                 fi
12626                 rm $file
12627         done
12628
12629         rm -rf $dir
12630 }
12631
12632 function roc_hit() {
12633         local list=$(comma_list $(osts_nodes))
12634         echo $(get_osd_param $list '' stats |
12635                 awk '$1 == "cache_hit" {sum += $7}
12636                         END { printf("%0.0f", sum) }')
12637 }
12638
12639 function set_cache() {
12640         local on=1
12641
12642         if [ "$2" == "off" ]; then
12643                 on=0;
12644         fi
12645         local list=$(comma_list $(osts_nodes))
12646         set_osd_param $list '' $1_cache_enable $on
12647
12648         cancel_lru_locks osc
12649 }
12650
12651 test_151() {
12652         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12653         remote_ost_nodsh && skip "remote OST with nodsh"
12654
12655         local CPAGES=3
12656         local list=$(comma_list $(osts_nodes))
12657
12658         # check whether obdfilter is cache capable at all
12659         if ! get_osd_param $list '' read_cache_enable >/dev/null; then
12660                 skip "not cache-capable obdfilter"
12661         fi
12662
12663         # check cache is enabled on all obdfilters
12664         if get_osd_param $list '' read_cache_enable | grep 0; then
12665                 skip "oss cache is disabled"
12666         fi
12667
12668         set_osd_param $list '' writethrough_cache_enable 1
12669
12670         # check write cache is enabled on all obdfilters
12671         if get_osd_param $list '' writethrough_cache_enable | grep 0; then
12672                 skip "oss write cache is NOT enabled"
12673         fi
12674
12675         roc_hit_init
12676
12677         #define OBD_FAIL_OBD_NO_LRU  0x609
12678         do_nodes $list $LCTL set_param fail_loc=0x609
12679
12680         # pages should be in the case right after write
12681         dd if=/dev/urandom of=$DIR/$tfile bs=4k count=$CPAGES ||
12682                 error "dd failed"
12683
12684         local BEFORE=$(roc_hit)
12685         cancel_lru_locks osc
12686         cat $DIR/$tfile >/dev/null
12687         local AFTER=$(roc_hit)
12688
12689         do_nodes $list $LCTL set_param fail_loc=0
12690
12691         if ! let "AFTER - BEFORE == CPAGES"; then
12692                 error "NOT IN CACHE: before: $BEFORE, after: $AFTER"
12693         fi
12694
12695         # the following read invalidates the cache
12696         cancel_lru_locks osc
12697         set_osd_param $list '' read_cache_enable 0
12698         cat $DIR/$tfile >/dev/null
12699
12700         # now data shouldn't be found in the cache
12701         BEFORE=$(roc_hit)
12702         cancel_lru_locks osc
12703         cat $DIR/$tfile >/dev/null
12704         AFTER=$(roc_hit)
12705         if let "AFTER - BEFORE != 0"; then
12706                 error "IN CACHE: before: $BEFORE, after: $AFTER"
12707         fi
12708
12709         set_osd_param $list '' read_cache_enable 1
12710         rm -f $DIR/$tfile
12711 }
12712 run_test 151 "test cache on oss and controls ==============================="
12713
12714 test_152() {
12715         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12716
12717         local TF="$TMP/$tfile"
12718
12719         # simulate ENOMEM during write
12720 #define OBD_FAIL_OST_NOMEM      0x226
12721         lctl set_param fail_loc=0x80000226
12722         dd if=/dev/urandom of=$TF bs=6096 count=1 || error "dd failed"
12723         cp $TF $DIR/$tfile
12724         sync || error "sync failed"
12725         lctl set_param fail_loc=0
12726
12727         # discard client's cache
12728         cancel_lru_locks osc
12729
12730         # simulate ENOMEM during read
12731         lctl set_param fail_loc=0x80000226
12732         cmp $TF $DIR/$tfile || error "cmp failed"
12733         lctl set_param fail_loc=0
12734
12735         rm -f $TF
12736 }
12737 run_test 152 "test read/write with enomem ============================"
12738
12739 test_153() {
12740         $MULTIOP $DIR/$tfile Ow4096Ycu || error "multiop failed"
12741 }
12742 run_test 153 "test if fdatasync does not crash ======================="
12743
12744 dot_lustre_fid_permission_check() {
12745         local fid=$1
12746         local ffid=$MOUNT/.lustre/fid/$fid
12747         local test_dir=$2
12748
12749         echo "stat fid $fid"
12750         stat $ffid > /dev/null || error "stat $ffid failed."
12751         echo "touch fid $fid"
12752         touch $ffid || error "touch $ffid failed."
12753         echo "write to fid $fid"
12754         cat /etc/hosts > $ffid || error "write $ffid failed."
12755         echo "read fid $fid"
12756         diff /etc/hosts $ffid || error "read $ffid failed."
12757         echo "append write to fid $fid"
12758         cat /etc/hosts >> $ffid || error "append write $ffid failed."
12759         echo "rename fid $fid"
12760         mv $ffid $test_dir/$tfile.1 &&
12761                 error "rename $ffid to $tfile.1 should fail."
12762         touch $test_dir/$tfile.1
12763         mv $test_dir/$tfile.1 $ffid &&
12764                 error "rename $tfile.1 to $ffid should fail."
12765         rm -f $test_dir/$tfile.1
12766         echo "truncate fid $fid"
12767         $TRUNCATE $ffid 777 || error "truncate $ffid failed."
12768         echo "link fid $fid"
12769         ln -f $ffid $test_dir/tfile.lnk || error "link $ffid failed."
12770         if [[ $($LCTL get_param -n mdc.*-mdc-*.connect_flags) =~ acl ]]; then
12771                 echo "setfacl fid $fid"
12772                 setfacl -R -m u:bin:rwx $ffid || error "setfacl $ffid failed."
12773                 echo "getfacl fid $fid"
12774                 getfacl $ffid >/dev/null || error "getfacl $ffid failed."
12775         fi
12776         echo "unlink fid $fid"
12777         unlink $MOUNT/.lustre/fid/$fid && error "unlink $ffid should fail."
12778         echo "mknod fid $fid"
12779         mknod $ffid c 1 3 && error "mknod $ffid should fail."
12780
12781         fid=[0xf00000400:0x1:0x0]
12782         ffid=$MOUNT/.lustre/fid/$fid
12783
12784         echo "stat non-exist fid $fid"
12785         stat $ffid > /dev/null && error "stat non-exist $ffid should fail."
12786         echo "write to non-exist fid $fid"
12787         cat /etc/hosts > $ffid && error "write non-exist $ffid should fail."
12788         echo "link new fid $fid"
12789         ln $test_dir/$tfile $ffid && error "link $ffid should fail."
12790
12791         mkdir -p $test_dir/$tdir
12792         touch $test_dir/$tdir/$tfile
12793         fid=$($LFS path2fid $test_dir/$tdir)
12794         rc=$?
12795         [ $rc -ne 0 ] &&
12796                 error "error: could not get fid for $test_dir/$dir/$tfile."
12797
12798         ffid=$MOUNT/.lustre/fid/$fid
12799
12800         echo "ls $fid"
12801         ls $ffid > /dev/null || error "ls $ffid failed."
12802         echo "touch $fid/$tfile.1"
12803         touch $ffid/$tfile.1 || error "touch $ffid/$tfile.1 failed."
12804
12805         echo "touch $MOUNT/.lustre/fid/$tfile"
12806         touch $MOUNT/.lustre/fid/$tfile && \
12807                 error "touch $MOUNT/.lustre/fid/$tfile should fail."
12808
12809         echo "setxattr to $MOUNT/.lustre/fid"
12810         setfattr -n trusted.name1 -v value1 $MOUNT/.lustre/fid
12811
12812         echo "listxattr for $MOUNT/.lustre/fid"
12813         getfattr -d -m "^trusted" $MOUNT/.lustre/fid
12814
12815         echo "delxattr from $MOUNT/.lustre/fid"
12816         setfattr -x trusted.name1 $MOUNT/.lustre/fid
12817
12818         echo "touch invalid fid: $MOUNT/.lustre/fid/[0x200000400:0x2:0x3]"
12819         touch $MOUNT/.lustre/fid/[0x200000400:0x2:0x3] &&
12820                 error "touch invalid fid should fail."
12821
12822         echo "touch non-normal fid: $MOUNT/.lustre/fid/[0x1:0x2:0x0]"
12823         touch $MOUNT/.lustre/fid/[0x1:0x2:0x0] &&
12824                 error "touch non-normal fid should fail."
12825
12826         echo "rename $tdir to $MOUNT/.lustre/fid"
12827         mrename $test_dir/$tdir $MOUNT/.lustre/fid &&
12828                 error "rename to $MOUNT/.lustre/fid should fail."
12829
12830         if [ $MDS1_VERSION -ge $(version_code 2.3.51) ]
12831         then            # LU-3547
12832                 local old_obf_mode=$(stat --format="%a" $DIR/.lustre/fid)
12833                 local new_obf_mode=777
12834
12835                 echo "change mode of $DIR/.lustre/fid to $new_obf_mode"
12836                 chmod $new_obf_mode $DIR/.lustre/fid ||
12837                         error "chmod $new_obf_mode $DIR/.lustre/fid failed"
12838
12839                 local obf_mode=$(stat --format=%a $DIR/.lustre/fid)
12840                 [ $obf_mode -eq $new_obf_mode ] ||
12841                         error "stat $DIR/.lustre/fid returned wrong mode $obf_mode"
12842
12843                 echo "restore mode of $DIR/.lustre/fid to $old_obf_mode"
12844                 chmod $old_obf_mode $DIR/.lustre/fid ||
12845                         error "chmod $old_obf_mode $DIR/.lustre/fid failed"
12846         fi
12847
12848         $OPENFILE -f O_LOV_DELAY_CREATE:O_CREAT $test_dir/$tfile-2
12849         fid=$($LFS path2fid $test_dir/$tfile-2)
12850
12851         if [ $MDS1_VERSION -ge $(version_code 2.6.50) ]
12852         then # LU-5424
12853                 echo "cp /etc/passwd $MOUNT/.lustre/fid/$fid"
12854                 cp /etc/passwd $MOUNT/.lustre/fid/$fid ||
12855                         error "create lov data thru .lustre failed"
12856         fi
12857         echo "cp /etc/passwd $test_dir/$tfile-2"
12858         cp /etc/passwd $test_dir/$tfile-2 ||
12859                 error "copy to $test_dir/$tfile-2 failed."
12860         echo "diff /etc/passwd $MOUNT/.lustre/fid/$fid"
12861         diff /etc/passwd $MOUNT/.lustre/fid/$fid ||
12862                 error "diff /etc/passwd $MOUNT/.lustre/fid/$fid failed."
12863
12864         rm -rf $test_dir/tfile.lnk
12865         rm -rf $test_dir/$tfile-2
12866 }
12867
12868 test_154A() {
12869         [[ $MDS1_VERSION -lt $(version_code 2.4.1) ]] &&
12870                 skip "Need MDS version at least 2.4.1"
12871
12872         local tf=$DIR/$tfile
12873         touch $tf
12874
12875         local fid=$($LFS path2fid $tf)
12876         [ -z "$fid" ] && error "path2fid unable to get $tf FID"
12877
12878         # check that we get the same pathname back
12879         local found=$($LFS fid2path $MOUNT "$fid")
12880         [ -z "$found" ] && error "fid2path unable to get '$fid' path"
12881         [ "$found" == "$tf" ] ||
12882                 error "fid2path($fid=path2fid($tf)) = $found != $tf"
12883 }
12884 run_test 154A "lfs path2fid and fid2path basic checks"
12885
12886 test_154B() {
12887         [[ $MDS1_VERSION -lt $(version_code 2.4.1) ]] &&
12888                 skip "Need MDS version at least 2.4.1"
12889
12890         mkdir -p $DIR/$tdir || error "mkdir $tdir failed"
12891         touch $DIR/$tdir/$tfile || error "touch $DIR/$tdir/$tfile failed"
12892         local linkea=$($LL_DECODE_LINKEA $DIR/$tdir/$tfile | grep 'pfid')
12893         [ -z "$linkea" ] && error "decode linkea $DIR/$tdir/$tfile failed"
12894
12895         local name=$(echo $linkea | awk '/pfid/ {print $5}' | sed -e "s/'//g")
12896         local PFID=$(echo $linkea | awk '/pfid/ {print $3}' | sed -e "s/,//g")
12897
12898         # check that we get the same pathname
12899         echo "PFID: $PFID, name: $name"
12900         local FOUND=$($LFS fid2path $MOUNT "$PFID")
12901         [ -z "$FOUND" ] && error "fid2path unable to get $PFID path"
12902         [ "$FOUND/$name" != "$DIR/$tdir/$tfile" ] &&
12903                 error "ll_decode_linkea has $FOUND/$name != $DIR/$tdir/$tfile"
12904
12905         rm -rf $DIR/$tdir || error "Can not delete directory $DIR/$tdir"
12906 }
12907 run_test 154B "verify the ll_decode_linkea tool"
12908
12909 test_154a() {
12910         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12911         [ -n "$FILESET" ] && skip "SKIP due to FILESET set"
12912         [[ $MDS1_VERSION -ge $(version_code 2.2.51) ]] ||
12913                 skip "Need MDS version at least 2.2.51"
12914         [ -z "$(which setfacl)" ] && skip_env "must have setfacl tool"
12915
12916         cp /etc/hosts $DIR/$tfile
12917
12918         fid=$($LFS path2fid $DIR/$tfile)
12919         rc=$?
12920         [ $rc -ne 0 ] && error "error: could not get fid for $DIR/$tfile."
12921
12922         dot_lustre_fid_permission_check "$fid" $DIR ||
12923                 error "dot lustre permission check $fid failed"
12924
12925         ls -a $MOUNT | grep "\.lustre" && error ".lustre should not be listed"
12926
12927         rm -rf $MOUNT/.lustre && error ".lustre is not allowed to be unlinked"
12928
12929         touch $MOUNT/.lustre/file &&
12930                 error "creation is not allowed under .lustre"
12931
12932         mkdir $MOUNT/.lustre/dir &&
12933                 error "mkdir is not allowed under .lustre"
12934
12935         rm -rf $DIR/$tfile
12936 }
12937 run_test 154a "Open-by-FID"
12938
12939 test_154b() {
12940         [ $PARALLEL == "yes" ] && skip "skip parallel run"
12941         [ -n "$FILESET" ] && skip "SKIP due to FILESET set"
12942         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
12943         [[ $MDS1_VERSION -ge $(version_code 2.2.51) ]] ||
12944                 skip "Need MDS version at least 2.2.51"
12945
12946         local remote_dir=$DIR/$tdir/remote_dir
12947         local MDTIDX=1
12948         local rc=0
12949
12950         mkdir -p $DIR/$tdir
12951         $LFS mkdir -i $MDTIDX $remote_dir ||
12952                 error "create remote directory failed"
12953
12954         cp /etc/hosts $remote_dir/$tfile
12955
12956         fid=$($LFS path2fid $remote_dir/$tfile)
12957         rc=$?
12958         [ $rc -ne 0 ] && error "error: could not get fid for $remote_dir/$tfile"
12959
12960         dot_lustre_fid_permission_check "$fid" $remote_dir ||
12961                 error "dot lustre permission check $fid failed"
12962         rm -rf $DIR/$tdir
12963 }
12964 run_test 154b "Open-by-FID for remote directory"
12965
12966 test_154c() {
12967         [[ $MDS1_VERSION -lt $(version_code 2.4.1) ]] &&
12968                 skip "Need MDS version at least 2.4.1"
12969
12970         touch $DIR/$tfile.1 $DIR/$tfile.2 $DIR/$tfile.3
12971         local FID1=$($LFS path2fid $DIR/$tfile.1)
12972         local FID2=$($LFS path2fid $DIR/$tfile.2)
12973         local FID3=$($LFS path2fid $DIR/$tfile.3)
12974
12975         local N=1
12976         $LFS path2fid $DIR/$tfile.[123] | while read PATHNAME FID; do
12977                 [ "$PATHNAME" = "$DIR/$tfile.$N:" ] ||
12978                         error "path2fid pathname $PATHNAME != $DIR/$tfile.$N:"
12979                 local want=FID$N
12980                 [ "$FID" = "${!want}" ] ||
12981                         error "path2fid $PATHNAME FID $FID != FID$N ${!want}"
12982                 N=$((N + 1))
12983         done
12984
12985         $LFS fid2path $MOUNT "$FID1" "$FID2" "$FID3" | while read PATHNAME;
12986         do
12987                 [ "$PATHNAME" = "$DIR/$tfile.$N" ] ||
12988                         error "fid2path pathname $PATHNAME != $DIR/$tfile.$N:"
12989                 N=$((N + 1))
12990         done
12991 }
12992 run_test 154c "lfs path2fid and fid2path multiple arguments"
12993
12994 test_154d() {
12995         remote_mds_nodsh && skip "remote MDS with nodsh"
12996         [[ $MDS1_VERSION -lt $(version_code 2.5.53) ]] &&
12997                 skip "Need MDS version at least 2.5.53"
12998
12999         if remote_mds; then
13000                 nid=$($LCTL list_nids | sed  "s/\./\\\./g")
13001         else
13002                 nid="0@lo"
13003         fi
13004         local proc_ofile="mdt.*.exports.'$nid'.open_files"
13005         local fd
13006         local cmd
13007
13008         rm -f $DIR/$tfile
13009         touch $DIR/$tfile
13010
13011         local fid=$($LFS path2fid $DIR/$tfile)
13012         # Open the file
13013         fd=$(free_fd)
13014         cmd="exec $fd<$DIR/$tfile"
13015         eval $cmd
13016         local fid_list=$(do_facet $SINGLEMDS $LCTL get_param $proc_ofile)
13017         echo "$fid_list" | grep "$fid"
13018         rc=$?
13019
13020         cmd="exec $fd>/dev/null"
13021         eval $cmd
13022         if [ $rc -ne 0 ]; then
13023                 error "FID $fid not found in open files list $fid_list"
13024         fi
13025 }
13026 run_test 154d "Verify open file fid"
13027
13028 test_154e()
13029 {
13030         [[ $MDS1_VERSION -lt $(version_code 2.6.50) ]] &&
13031                 skip "Need MDS version at least 2.6.50"
13032
13033         if ls -a $MOUNT | grep -q '^\.lustre$'; then
13034                 error ".lustre returned by readdir"
13035         fi
13036 }
13037 run_test 154e ".lustre is not returned by readdir"
13038
13039 test_154f() {
13040         [ -n "$FILESET" ] && skip "SKIP due to FILESET set"
13041
13042         # create parent directory on a single MDT to avoid cross-MDT hardlinks
13043         test_mkdir -p -c1 $DIR/$tdir/d
13044         # test dirs inherit from its stripe
13045         mkdir -p $DIR/$tdir/d/foo1 || error "mkdir error"
13046         mkdir -p $DIR/$tdir/d/foo2 || error "mkdir error"
13047         cp /etc/hosts $DIR/$tdir/d/foo1/$tfile
13048         ln $DIR/$tdir/d/foo1/$tfile $DIR/$tdir/d/foo2/link
13049         touch $DIR/f
13050
13051         # get fid of parents
13052         local FID0=$($LFS path2fid $DIR/$tdir/d)
13053         local FID1=$($LFS path2fid $DIR/$tdir/d/foo1)
13054         local FID2=$($LFS path2fid $DIR/$tdir/d/foo2)
13055         local FID3=$($LFS path2fid $DIR)
13056
13057         # check that path2fid --parents returns expected <parent_fid>/name
13058         # 1) test for a directory (single parent)
13059         local parent=$($LFS path2fid --parents $DIR/$tdir/d/foo1)
13060         [ "$parent" == "$FID0/foo1" ] ||
13061                 error "expected parent: $FID0/foo1, got: $parent"
13062
13063         # 2) test for a file with nlink > 1 (multiple parents)
13064         parent=$($LFS path2fid --parents $DIR/$tdir/d/foo1/$tfile)
13065         echo "$parent" | grep -F "$FID1/$tfile" ||
13066                 error "$FID1/$tfile not returned in parent list"
13067         echo "$parent" | grep -F "$FID2/link" ||
13068                 error "$FID2/link not returned in parent list"
13069
13070         # 3) get parent by fid
13071         local file_fid=$($LFS path2fid $DIR/$tdir/d/foo1/$tfile)
13072         parent=$($LFS path2fid --parents $MOUNT/.lustre/fid/$file_fid)
13073         echo "$parent" | grep -F "$FID1/$tfile" ||
13074                 error "$FID1/$tfile not returned in parent list (by fid)"
13075         echo "$parent" | grep -F "$FID2/link" ||
13076                 error "$FID2/link not returned in parent list (by fid)"
13077
13078         # 4) test for entry in root directory
13079         parent=$($LFS path2fid --parents $DIR/f)
13080         echo "$parent" | grep -F "$FID3/f" ||
13081                 error "$FID3/f not returned in parent list"
13082
13083         # 5) test it on root directory
13084         [ -z "$($LFS path2fid --parents $MOUNT 2>/dev/null)" ] ||
13085                 error "$MOUNT should not have parents"
13086
13087         # enable xattr caching and check that linkea is correctly updated
13088         local save="$TMP/$TESTSUITE-$TESTNAME.parameters"
13089         save_lustre_params client "llite.*.xattr_cache" > $save
13090         lctl set_param llite.*.xattr_cache 1
13091
13092         # 6.1) linkea update on rename
13093         mv $DIR/$tdir/d/foo1/$tfile $DIR/$tdir/d/foo2/$tfile.moved
13094
13095         # get parents by fid
13096         parent=$($LFS path2fid --parents $MOUNT/.lustre/fid/$file_fid)
13097         # foo1 should no longer be returned in parent list
13098         echo "$parent" | grep -F "$FID1" &&
13099                 error "$FID1 should no longer be in parent list"
13100         # the new path should appear
13101         echo "$parent" | grep -F "$FID2/$tfile.moved" ||
13102                 error "$FID2/$tfile.moved is not in parent list"
13103
13104         # 6.2) linkea update on unlink
13105         rm -f $DIR/$tdir/d/foo2/link
13106         parent=$($LFS path2fid --parents $MOUNT/.lustre/fid/$file_fid)
13107         # foo2/link should no longer be returned in parent list
13108         echo "$parent" | grep -F "$FID2/link" &&
13109                 error "$FID2/link should no longer be in parent list"
13110         true
13111
13112         rm -f $DIR/f
13113         restore_lustre_params < $save
13114         rm -f $save
13115 }
13116 run_test 154f "get parent fids by reading link ea"
13117
13118 test_154g()
13119 {
13120         [ -n "$FILESET" ] && skip "SKIP due to FILESET set"
13121         [[ $MDS1_VERSION -ge $(version_code 2.6.92) &&
13122            $CLIENT_VERSION -gt $(version_code 2.6.99) ]] ||
13123                 skip "Need MDS version at least 2.6.92"
13124
13125         mkdir -p $DIR/$tdir
13126         llapi_fid_test -d $DIR/$tdir
13127 }
13128 run_test 154g "various llapi FID tests"
13129
13130 test_155_small_load() {
13131     local temp=$TMP/$tfile
13132     local file=$DIR/$tfile
13133
13134     dd if=/dev/urandom of=$temp bs=6096 count=1 || \
13135         error "dd of=$temp bs=6096 count=1 failed"
13136     cp $temp $file
13137     cancel_lru_locks $OSC
13138     cmp $temp $file || error "$temp $file differ"
13139
13140     $TRUNCATE $temp 6000
13141     $TRUNCATE $file 6000
13142     cmp $temp $file || error "$temp $file differ (truncate1)"
13143
13144     echo "12345" >>$temp
13145     echo "12345" >>$file
13146     cmp $temp $file || error "$temp $file differ (append1)"
13147
13148     echo "12345" >>$temp
13149     echo "12345" >>$file
13150     cmp $temp $file || error "$temp $file differ (append2)"
13151
13152     rm -f $temp $file
13153     true
13154 }
13155
13156 test_155_big_load() {
13157         remote_ost_nodsh && skip "remote OST with nodsh"
13158
13159         local temp=$TMP/$tfile
13160         local file=$DIR/$tfile
13161
13162         free_min_max
13163         local cache_size=$(do_facet ost$((MAXI+1)) \
13164                 "awk '/cache/ {sum+=\\\$4} END {print sum}' /proc/cpuinfo")
13165         local large_file_size=$((cache_size * 2))
13166
13167         echo "OSS cache size: $cache_size KB"
13168         echo "Large file size: $large_file_size KB"
13169
13170         [ $MAXV -le $large_file_size ] &&
13171                 skip_env "max available OST size needs > $large_file_size KB"
13172
13173         $LFS setstripe $file -c 1 -i $MAXI || error "$LFS setstripe $file failed"
13174
13175         dd if=/dev/urandom of=$temp bs=$large_file_size count=1k ||
13176                 error "dd of=$temp bs=$large_file_size count=1k failed"
13177         cp $temp $file
13178         ls -lh $temp $file
13179         cancel_lru_locks osc
13180         cmp $temp $file || error "$temp $file differ"
13181
13182         rm -f $temp $file
13183         true
13184 }
13185
13186 save_writethrough() {
13187         local facets=$(get_facets OST)
13188
13189         save_lustre_params $facets "osd-*.*.writethrough_cache_enable" > $1
13190 }
13191
13192 test_155a() {
13193         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13194
13195         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
13196
13197         save_writethrough $p
13198
13199         set_cache read on
13200         set_cache writethrough on
13201         test_155_small_load
13202         restore_lustre_params < $p
13203         rm -f $p
13204 }
13205 run_test 155a "Verify small file correctness: read cache:on write_cache:on"
13206
13207 test_155b() {
13208         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13209
13210         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
13211
13212         save_writethrough $p
13213
13214         set_cache read on
13215         set_cache writethrough off
13216         test_155_small_load
13217         restore_lustre_params < $p
13218         rm -f $p
13219 }
13220 run_test 155b "Verify small file correctness: read cache:on write_cache:off"
13221
13222 test_155c() {
13223         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13224
13225         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
13226
13227         save_writethrough $p
13228
13229         set_cache read off
13230         set_cache writethrough on
13231         test_155_small_load
13232         restore_lustre_params < $p
13233         rm -f $p
13234 }
13235 run_test 155c "Verify small file correctness: read cache:off write_cache:on"
13236
13237 test_155d() {
13238         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13239
13240         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
13241
13242         save_writethrough $p
13243
13244         set_cache read off
13245         set_cache writethrough off
13246         test_155_small_load
13247         restore_lustre_params < $p
13248         rm -f $p
13249 }
13250 run_test 155d "Verify small file correctness: read cache:off write_cache:off"
13251
13252 test_155e() {
13253         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13254
13255         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
13256
13257         save_writethrough $p
13258
13259         set_cache read on
13260         set_cache writethrough on
13261         test_155_big_load
13262         restore_lustre_params < $p
13263         rm -f $p
13264 }
13265 run_test 155e "Verify big file correctness: read cache:on write_cache:on"
13266
13267 test_155f() {
13268         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13269
13270         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
13271
13272         save_writethrough $p
13273
13274         set_cache read on
13275         set_cache writethrough off
13276         test_155_big_load
13277         restore_lustre_params < $p
13278         rm -f $p
13279 }
13280 run_test 155f "Verify big file correctness: read cache:on write_cache:off"
13281
13282 test_155g() {
13283         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13284
13285         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
13286
13287         save_writethrough $p
13288
13289         set_cache read off
13290         set_cache writethrough on
13291         test_155_big_load
13292         restore_lustre_params < $p
13293         rm -f $p
13294 }
13295 run_test 155g "Verify big file correctness: read cache:off write_cache:on"
13296
13297 test_155h() {
13298         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13299
13300         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
13301
13302         save_writethrough $p
13303
13304         set_cache read off
13305         set_cache writethrough off
13306         test_155_big_load
13307         restore_lustre_params < $p
13308         rm -f $p
13309 }
13310 run_test 155h "Verify big file correctness: read cache:off write_cache:off"
13311
13312 test_156() {
13313         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13314         remote_ost_nodsh && skip "remote OST with nodsh"
13315         [ $OST1_VERSION -lt $(version_code 2.6.93) ] &&
13316                 skip "stats not implemented on old servers"
13317         [ "$ost1_FSTYPE" = "zfs" ] &&
13318                 skip "LU-1956/LU-2261: stats not implemented on OSD ZFS"
13319
13320         local CPAGES=3
13321         local BEFORE
13322         local AFTER
13323         local file="$DIR/$tfile"
13324         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
13325
13326         save_writethrough $p
13327         roc_hit_init
13328
13329         log "Turn on read and write cache"
13330         set_cache read on
13331         set_cache writethrough on
13332
13333         log "Write data and read it back."
13334         log "Read should be satisfied from the cache."
13335         dd if=/dev/urandom of=$file bs=4k count=$CPAGES || error "dd failed"
13336         BEFORE=$(roc_hit)
13337         cancel_lru_locks osc
13338         cat $file >/dev/null
13339         AFTER=$(roc_hit)
13340         if ! let "AFTER - BEFORE == CPAGES"; then
13341                 error "NOT IN CACHE: before: $BEFORE, after: $AFTER"
13342         else
13343                 log "cache hits:: before: $BEFORE, after: $AFTER"
13344         fi
13345
13346         log "Read again; it should be satisfied from the cache."
13347         BEFORE=$AFTER
13348         cancel_lru_locks osc
13349         cat $file >/dev/null
13350         AFTER=$(roc_hit)
13351         if ! let "AFTER - BEFORE == CPAGES"; then
13352                 error "NOT IN CACHE: before: $BEFORE, after: $AFTER"
13353         else
13354                 log "cache hits:: before: $BEFORE, after: $AFTER"
13355         fi
13356
13357         log "Turn off the read cache and turn on the write cache"
13358         set_cache read off
13359         set_cache writethrough on
13360
13361         log "Read again; it should be satisfied from the cache."
13362         BEFORE=$(roc_hit)
13363         cancel_lru_locks osc
13364         cat $file >/dev/null
13365         AFTER=$(roc_hit)
13366         if ! let "AFTER - BEFORE == CPAGES"; then
13367                 error "NOT IN CACHE: before: $BEFORE, after: $AFTER"
13368         else
13369                 log "cache hits:: before: $BEFORE, after: $AFTER"
13370         fi
13371
13372         log "Read again; it should not be satisfied from the cache."
13373         BEFORE=$AFTER
13374         cancel_lru_locks osc
13375         cat $file >/dev/null
13376         AFTER=$(roc_hit)
13377         if ! let "AFTER - BEFORE == 0"; then
13378                 error "IN CACHE: before: $BEFORE, after: $AFTER"
13379         else
13380                 log "cache hits:: before: $BEFORE, after: $AFTER"
13381         fi
13382
13383         log "Write data and read it back."
13384         log "Read should be satisfied from the cache."
13385         dd if=/dev/urandom of=$file bs=4k count=$CPAGES || error "dd failed"
13386         BEFORE=$(roc_hit)
13387         cancel_lru_locks osc
13388         cat $file >/dev/null
13389         AFTER=$(roc_hit)
13390         if ! let "AFTER - BEFORE == CPAGES"; then
13391                 error "NOT IN CACHE: before: $BEFORE, after: $AFTER"
13392         else
13393                 log "cache hits:: before: $BEFORE, after: $AFTER"
13394         fi
13395
13396         log "Read again; it should not be satisfied from the cache."
13397         BEFORE=$AFTER
13398         cancel_lru_locks osc
13399         cat $file >/dev/null
13400         AFTER=$(roc_hit)
13401         if ! let "AFTER - BEFORE == 0"; then
13402                 error "IN CACHE: before: $BEFORE, after: $AFTER"
13403         else
13404                 log "cache hits:: before: $BEFORE, after: $AFTER"
13405         fi
13406
13407         log "Turn off read and write cache"
13408         set_cache read off
13409         set_cache writethrough off
13410
13411         log "Write data and read it back"
13412         log "It should not be satisfied from the cache."
13413         rm -f $file
13414         dd if=/dev/urandom of=$file bs=4k count=$CPAGES || error "dd failed"
13415         cancel_lru_locks osc
13416         BEFORE=$(roc_hit)
13417         cat $file >/dev/null
13418         AFTER=$(roc_hit)
13419         if ! let "AFTER - BEFORE == 0"; then
13420                 error_ignore bz20762 "IN CACHE: before: $BEFORE, after: $AFTER"
13421         else
13422                 log "cache hits:: before: $BEFORE, after: $AFTER"
13423         fi
13424
13425         log "Turn on the read cache and turn off the write cache"
13426         set_cache read on
13427         set_cache writethrough off
13428
13429         log "Write data and read it back"
13430         log "It should not be satisfied from the cache."
13431         rm -f $file
13432         dd if=/dev/urandom of=$file bs=4k count=$CPAGES || error "dd failed"
13433         BEFORE=$(roc_hit)
13434         cancel_lru_locks osc
13435         cat $file >/dev/null
13436         AFTER=$(roc_hit)
13437         if ! let "AFTER - BEFORE == 0"; then
13438                 error_ignore bz20762 "IN CACHE: before: $BEFORE, after: $AFTER"
13439         else
13440                 log "cache hits:: before: $BEFORE, after: $AFTER"
13441         fi
13442
13443         log "Read again; it should be satisfied from the cache."
13444         BEFORE=$(roc_hit)
13445         cancel_lru_locks osc
13446         cat $file >/dev/null
13447         AFTER=$(roc_hit)
13448         if ! let "AFTER - BEFORE == CPAGES"; then
13449                 error "NOT IN CACHE: before: $BEFORE, after: $AFTER"
13450         else
13451                 log "cache hits:: before: $BEFORE, after: $AFTER"
13452         fi
13453
13454         restore_lustre_params < $p
13455         rm -f $p $file
13456 }
13457 run_test 156 "Verification of tunables"
13458
13459 test_160a() {
13460         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13461         remote_mds_nodsh && skip "remote MDS with nodsh"
13462         [ $MDS1_VERSION -ge $(version_code 2.2.0) ] ||
13463                 skip "Need MDS version at least 2.2.0"
13464
13465         changelog_register || error "changelog_register failed"
13466         local cl_user="${CL_USERS[$SINGLEMDS]%% *}"
13467         changelog_users $SINGLEMDS | grep -q $cl_user ||
13468                 error "User $cl_user not found in changelog_users"
13469
13470         # change something
13471         test_mkdir -p $DIR/$tdir/pics/2008/zachy
13472         changelog_clear 0 || error "changelog_clear failed"
13473         touch $DIR/$tdir/pics/2008/zachy/$tfile                 # open 1
13474         cp /etc/hosts $DIR/$tdir/pics/2008/zachy/pic1.jpg       # open 2
13475         mv $DIR/$tdir/pics/2008/zachy $DIR/$tdir/pics/zach
13476         ln $DIR/$tdir/pics/zach/pic1.jpg $DIR/$tdir/pics/2008/portland.jpg
13477         ln -s $DIR/$tdir/pics/2008/portland.jpg $DIR/$tdir/pics/desktop.jpg
13478         rm $DIR/$tdir/pics/desktop.jpg
13479
13480         changelog_dump | tail -10
13481
13482         echo "verifying changelog mask"
13483         changelog_chmask "-MKDIR"
13484         changelog_chmask "-CLOSE"
13485
13486         test_mkdir -p $DIR/$tdir/pics/zach/sofia                # not logged
13487         echo "zzzzzz" > $DIR/$tdir/pics/zach/file               # not logged
13488
13489         changelog_chmask "+MKDIR"
13490         changelog_chmask "+CLOSE"
13491
13492         test_mkdir -p $DIR/$tdir/pics/2008/sofia                # mkdir 1
13493         echo "zzzzzz" > $DIR/$tdir/pics/zach/file               # open 3
13494
13495         changelog_dump | tail -10
13496         MKDIRS=$(changelog_dump | grep -c "MKDIR")
13497         CLOSES=$(changelog_dump | grep -c "CLOSE")
13498         [ $MKDIRS -eq 1 ] || error "MKDIR changelog mask count $MKDIRS != 1"
13499         [ $CLOSES -eq 3 ] || error "CLOSE changelog mask count $CLOSES != 3"
13500
13501         # verify contents
13502         echo "verifying target fid"
13503         local fidc=$(changelog_extract_field "CREAT" "$tfile" "t=")
13504         local fidf=$($LFS path2fid $DIR/$tdir/pics/zach/$tfile)
13505         [ "$fidc" == "$fidf" ] ||
13506                 error "changelog '$tfile' fid $fidc != file fid $fidf"
13507         echo "verifying parent fid"
13508         # The FID returned from the Changelog may be the directory shard on
13509         # a different MDT, and not the FID returned by path2fid on the parent.
13510         # Instead of comparing FIDs, verify that fid2path(fidp) is correct,
13511         # since this is what will matter when recreating this file in the tree.
13512         local fidp=$(changelog_extract_field "CREAT" "$tfile" "p=")
13513         local pathp=$($LFS fid2path $MOUNT "$fidp")
13514         [ "${pathp%/}" == "$DIR/$tdir/pics/zach" ] ||
13515                 error "changelog fid2path($fidc) $pathp != $DIR/$tdir/pics/zach"
13516
13517         echo "getting records for $cl_user"
13518         changelog_users $SINGLEMDS
13519         local user_rec1=$(changelog_user_rec $SINGLEMDS $cl_user)
13520         local nclr=3
13521         __changelog_clear $SINGLEMDS $cl_user +$nclr ||
13522                 error "changelog_clear failed"
13523         local user_rec2=$(changelog_user_rec $SINGLEMDS $cl_user)
13524         echo "verifying user clear: $user_rec1 + $nclr == $user_rec2"
13525         [ $user_rec2 == $((user_rec1 + nclr)) ] ||
13526                 error "user index expect $user_rec1 + $nclr != $user_rec2"
13527
13528         local min0_rec=$(changelog_users $SINGLEMDS |
13529                 awk 'min == "" || $2 < min { min = $2 }; END { print min }')
13530         local first_rec=$($LFS changelog $(facet_svc $SINGLEMDS) |
13531                           awk '{ print $1; exit; }')
13532
13533         changelog_dump | tail -n 5
13534         echo "verifying user min purge: $min0_rec + 1 == $first_rec"
13535         [ $first_rec == $((min0_rec + 1)) ] ||
13536                 error "first index should be $min0_rec + 1 not $first_rec"
13537
13538         # LU-3446 changelog index reset on MDT restart
13539         local cur_rec1=$(changelog_users $SINGLEMDS |
13540                          awk '/^current.index:/ { print $NF }')
13541         changelog_clear 0 ||
13542                 error "clear all changelog records for $cl_user failed"
13543         stop $SINGLEMDS || error "Fail to stop $SINGLEMDS"
13544         start $SINGLEMDS $(mdsdevname ${SINGLEMDS//mds/}) $MDS_MOUNT_OPTS ||
13545                 error "Fail to start $SINGLEMDS"
13546         local cur_rec2=$(changelog_users $SINGLEMDS |
13547                          awk '/^current.index:/ { print $NF }')
13548         echo "verifying index survives MDT restart: $cur_rec1 == $cur_rec2"
13549         [ $cur_rec1 == $cur_rec2 ] ||
13550                 error "current index should be $cur_rec1 not $cur_rec2"
13551
13552         echo "verifying users from this test are deregistered"
13553         changelog_deregister || error "changelog_deregister failed"
13554         changelog_users $SINGLEMDS | grep -q $cl_user &&
13555                 error "User '$cl_user' still in changelog_users"
13556
13557         # lctl get_param -n mdd.*.changelog_users
13558         # current index: 144
13559         # ID    index (idle seconds)
13560         # cl3   144 (2)
13561         if ! changelog_users $SINGLEMDS | grep "^cl"; then
13562                 # this is the normal case where all users were deregistered
13563                 # make sure no new records are added when no users are present
13564                 local last_rec1=$(changelog_users $SINGLEMDS |
13565                                   awk '/^current.index:/ { print $NF }')
13566                 touch $DIR/$tdir/chloe
13567                 local last_rec2=$(changelog_users $SINGLEMDS |
13568                                   awk '/^current.index:/ { print $NF }')
13569                 echo "verify changelogs are off: $last_rec1 == $last_rec2"
13570                 [ $last_rec1 == $last_rec2 ] || error "changelogs not off"
13571         else
13572                 # any changelog users must be leftovers from a previous test
13573                 changelog_users $SINGLEMDS
13574                 echo "other changelog users; can't verify off"
13575         fi
13576 }
13577 run_test 160a "changelog sanity"
13578
13579 test_160b() { # LU-3587
13580         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13581         remote_mds_nodsh && skip "remote MDS with nodsh"
13582         [ $MDS1_VERSION -ge $(version_code 2.2.0) ] ||
13583                 skip "Need MDS version at least 2.2.0"
13584
13585         changelog_register || error "changelog_register failed"
13586         local cl_user="${CL_USERS[$SINGLEMDS]%% *}"
13587         changelog_users $SINGLEMDS | grep -q $cl_user ||
13588                 error "User '$cl_user' not found in changelog_users"
13589
13590         local longname1=$(str_repeat a 255)
13591         local longname2=$(str_repeat b 255)
13592
13593         cd $DIR
13594         echo "creating very long named file"
13595         touch $longname1 || error "create of '$longname1' failed"
13596         echo "renaming very long named file"
13597         mv $longname1 $longname2
13598
13599         changelog_dump | grep RENME | tail -n 5
13600         rm -f $longname2
13601 }
13602 run_test 160b "Verify that very long rename doesn't crash in changelog"
13603
13604 test_160c() {
13605         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13606         remote_mds_nodsh && skip "remote MDS with nodsh"
13607
13608         [[ $MDS1_VERSION -gt $(version_code 2.5.57) ]] ||
13609                 [[ $MDS1_VERSION -gt $(version_code 2.5.1) &&
13610                    $MDS1_VERSION -lt $(version_code 2.5.50) ]] ||
13611                 skip "Need MDS version at least 2.5.58 or 2.5.2+"
13612
13613         local rc=0
13614
13615         # Registration step
13616         changelog_register || error "changelog_register failed"
13617
13618         rm -rf $DIR/$tdir
13619         mkdir -p $DIR/$tdir
13620         $MCREATE $DIR/$tdir/foo_160c
13621         changelog_chmask "-TRUNC"
13622         $TRUNCATE $DIR/$tdir/foo_160c 200
13623         changelog_chmask "+TRUNC"
13624         $TRUNCATE $DIR/$tdir/foo_160c 199
13625         changelog_dump | tail -n 5
13626         local truncs=$(changelog_dump | tail -n 5 | grep -c TRUNC)
13627         [ $truncs -eq 1 ] || error "TRUNC changelog mask count $truncs != 1"
13628 }
13629 run_test 160c "verify that changelog log catch the truncate event"
13630
13631 test_160d() {
13632         remote_mds_nodsh && skip "remote MDS with nodsh"
13633         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
13634         [ $PARALLEL == "yes" ] && skip "skip parallel run"
13635         [[ $MDS1_VERSION -ge $(version_code 2.7.60) ]] ||
13636                 skip "Need MDS version at least 2.7.60"
13637
13638         # Registration step
13639         changelog_register || error "changelog_register failed"
13640
13641         mkdir -p $DIR/$tdir/migrate_dir
13642         changelog_clear 0 || error "changelog_clear failed"
13643
13644         $LFS migrate -m 1 $DIR/$tdir/migrate_dir || error "migrate fails"
13645         changelog_dump | tail -n 5
13646         local migrates=$(changelog_dump | grep -c "MIGRT")
13647         [ $migrates -eq 1 ] || error "MIGRATE changelog count $migrates != 1"
13648 }
13649 run_test 160d "verify that changelog log catch the migrate event"
13650
13651 test_160e() {
13652         remote_mds_nodsh && skip "remote MDS with nodsh"
13653
13654         # Create a user
13655         changelog_register || error "changelog_register failed"
13656
13657         # Delete a future user (expect fail)
13658         local MDT0=$(facet_svc $SINGLEMDS)
13659         do_facet $SINGLEMDS $LCTL --device $MDT0 changelog_deregister "cl77"
13660         local rc=$?
13661
13662         if [ $rc -eq 0 ]; then
13663                 error "Deleted non-existant user cl77"
13664         elif [ $rc -ne 2 ]; then
13665                 error "changelog_deregister failed with $rc, expect 2 (ENOENT)"
13666         fi
13667
13668         # Clear to a bad index (1 billion should be safe)
13669         $LFS changelog_clear $MDT0 "${CL_USERS[$SINGLEMDS]%% *}" 1000000000
13670         rc=$?
13671
13672         if [ $rc -eq 0 ]; then
13673                 error "Successfully cleared to invalid CL index"
13674         elif [ $rc -ne 22 ]; then
13675                 error "changelog_clear failed with $rc, expected 22 (EINVAL)"
13676         fi
13677 }
13678 run_test 160e "changelog negative testing (should return errors)"
13679
13680 test_160f() {
13681         remote_mds_nodsh && skip "remote MDS with nodsh" && return
13682         [[ $MDS1_VERSION -ge $(version_code 2.10.56) ]] ||
13683                 skip "Need MDS version at least 2.10.56"
13684
13685         local mdts=$(comma_list $(mdts_nodes))
13686
13687         # Create a user
13688         changelog_register || error "first changelog_register failed"
13689         changelog_register || error "second changelog_register failed"
13690         local cl_users
13691         declare -A cl_user1
13692         declare -A cl_user2
13693         local user_rec1
13694         local user_rec2
13695         local i
13696
13697         # generate some changelog records to accumulate on each MDT
13698         test_mkdir -c $MDSCOUNT $DIR/$tdir || error "test_mkdir $tdir failed"
13699         createmany -m $DIR/$tdir/$tfile $((MDSCOUNT * 2)) ||
13700                 error "create $DIR/$tdir/$tfile failed"
13701
13702         # check changelogs have been generated
13703         local nbcl=$(changelog_dump | wc -l)
13704         [[ $nbcl -eq 0 ]] && error "no changelogs found"
13705
13706         for param in "changelog_max_idle_time=10" \
13707                      "changelog_gc=1" \
13708                      "changelog_min_gc_interval=2" \
13709                      "changelog_min_free_cat_entries=3"; do
13710                 local MDT0=$(facet_svc $SINGLEMDS)
13711                 local var="${param%=*}"
13712                 local old=$(do_facet mds1 "$LCTL get_param -n mdd.$MDT0.$var")
13713
13714                 stack_trap "do_nodes $mdts $LCTL set_param mdd.*.$var=$old" EXIT
13715                 do_nodes $mdts $LCTL set_param mdd.*.$param
13716         done
13717
13718         # force cl_user2 to be idle (1st part)
13719         sleep 9
13720
13721         # simulate changelog catalog almost full
13722         #define OBD_FAIL_CAT_FREE_RECORDS       0x1313
13723         do_nodes $mdts $LCTL set_param fail_loc=0x1313 fail_val=3
13724
13725         for i in $(seq $MDSCOUNT); do
13726                 cl_users=(${CL_USERS[mds$i]})
13727                 cl_user1[mds$i]="${cl_users[0]}"
13728                 cl_user2[mds$i]="${cl_users[1]}"
13729
13730                 [ -n "${cl_user1[mds$i]}" ] ||
13731                         error "mds$i: no user registered"
13732                 [ -n "${cl_user2[mds$i]}" ] ||
13733                         error "mds$i: only ${cl_user2[mds$i]} is registered"
13734
13735                 user_rec1=$(changelog_user_rec mds$i ${cl_user1[mds$i]})
13736                 [ -n "$user_rec1" ] ||
13737                         error "mds$i: User ${cl_user1[mds$i]} not registered"
13738                 __changelog_clear mds$i ${cl_user1[mds$i]} +2
13739                 user_rec2=$(changelog_user_rec mds$i ${cl_user1[mds$i]})
13740                 [ -n "$user_rec2" ] ||
13741                         error "mds$i: User ${cl_user1[mds$i]} not registered"
13742                 echo "mds$i: verifying user ${cl_user1[mds$i]} clear: " \
13743                      "$user_rec1 + 2 == $user_rec2"
13744                 [ $((user_rec1 + 2)) == $user_rec2 ] ||
13745                         error "mds$i: user ${cl_user1[mds$i]} index expected " \
13746                               "$user_rec1 + 2, but is $user_rec2"
13747                 user_rec2=$(changelog_user_rec mds$i ${cl_user2[mds$i]})
13748                 [ -n "$user_rec2" ] ||
13749                         error "mds$i: User ${cl_user2[mds$i]} not registered"
13750                 [ $user_rec1 == $user_rec2 ] ||
13751                         error "mds$i: user ${cl_user2[mds$i]} index expected " \
13752                               "$user_rec1, but is $user_rec2"
13753         done
13754
13755         # force cl_user2 to be idle (2nd part) and to reach
13756         # changelog_max_idle_time
13757         sleep 2
13758
13759         # generate one more changelog to trigger fail_loc
13760         createmany -m $DIR/$tdir/${tfile}bis $((MDSCOUNT * 2)) ||
13761                 error "create $DIR/$tdir/${tfile}bis failed"
13762
13763         # ensure gc thread is done
13764         for i in $(mdts_nodes); do
13765                 wait_update $i \
13766                         "ps -e -o comm= | grep chlg_gc_thread" "" 20 ||
13767                         error "$i: GC-thread not done"
13768         done
13769
13770         local first_rec
13771         for i in $(seq $MDSCOUNT); do
13772                 # check cl_user1 still registered
13773                 changelog_users mds$i | grep -q "${cl_user1[mds$i]}" ||
13774                         error "mds$i: User ${cl_user1[mds$i]} not registered"
13775                 # check cl_user2 unregistered
13776                 changelog_users mds$i | grep -q "${cl_user2[mds$i]}" &&
13777                         error "mds$i: User ${cl_user2[mds$i]} still registered"
13778
13779                 # check changelogs are present and starting at $user_rec1 + 1
13780                 user_rec1=$(changelog_user_rec mds$i ${cl_user1[mds$i]})
13781                 [ -n "$user_rec1" ] ||
13782                         error "mds$i: User ${cl_user1[mds$i]} not registered"
13783                 first_rec=$($LFS changelog $(facet_svc mds$i) |
13784                             awk '{ print $1; exit; }')
13785
13786                 echo "mds$i: verifying first index $user_rec1 + 1 == $first_rec"
13787                 [ $((user_rec1 + 1)) == $first_rec ] ||
13788                         error "mds$i: first index should be $user_rec1 + 1, " \
13789                               "but is $first_rec"
13790         done
13791 }
13792 run_test 160f "changelog garbage collect (timestamped users)"
13793
13794 test_160g() {
13795         remote_mds_nodsh && skip "remote MDS with nodsh"
13796         [[ $MDS1_VERSION -ge $(version_code 2.10.56) ]] ||
13797                 skip "Need MDS version at least 2.10.56"
13798
13799         local mdts=$(comma_list $(mdts_nodes))
13800
13801         #define OBD_FAIL_TIME_IN_CHLOG_USER     0x1314
13802         do_nodes $mdts $LCTL set_param fail_loc=0x1314
13803
13804         # Create a user
13805         changelog_register || error "first changelog_register failed"
13806         changelog_register || error "second changelog_register failed"
13807         local cl_users
13808         declare -A cl_user1
13809         declare -A cl_user2
13810         local user_rec1
13811         local user_rec2
13812         local i
13813
13814         # generate some changelog records to accumulate on each MDT
13815         test_mkdir -c $MDSCOUNT $DIR/$tdir || error "mkdir $tdir failed"
13816         createmany -m $DIR/$tdir/$tfile $((MDSCOUNT * 2)) ||
13817                 error "create $DIR/$tdir/$tfile failed"
13818
13819         # check changelogs have been generated
13820         local nbcl=$(changelog_dump | wc -l)
13821         [[ $nbcl -eq 0 ]] && error "no changelogs found"
13822
13823         # reduce the max_idle_indexes value to make sure we exceed it
13824         max_ndx=$((nbcl / 2 - 1))
13825
13826         for param in "changelog_max_idle_indexes=$max_ndx" \
13827                      "changelog_gc=1" \
13828                      "changelog_min_gc_interval=2" \
13829                      "changelog_min_free_cat_entries=3"; do
13830                 local MDT0=$(facet_svc $SINGLEMDS)
13831                 local var="${param%=*}"
13832                 local old=$(do_facet mds1 "$LCTL get_param -n mdd.$MDT0.$var")
13833
13834                 stack_trap "do_nodes $mdts $LCTL set_param mdd.*.$var=$old" EXIT
13835                 do_nodes $mdts $LCTL set_param mdd.*.$param ||
13836                         error "unable to set mdd.*.$param"
13837         done
13838
13839         # simulate changelog catalog almost full
13840         #define OBD_FAIL_CAT_FREE_RECORDS       0x1313
13841         do_nodes $mdts $LCTL set_param fail_loc=0x1313 fail_val=3
13842
13843         for i in $(seq $MDSCOUNT); do
13844                 cl_users=(${CL_USERS[mds$i]})
13845                 cl_user1[mds$i]="${cl_users[0]}"
13846                 cl_user2[mds$i]="${cl_users[1]}"
13847
13848                 [ -n "${cl_user1[mds$i]}" ] ||
13849                         error "mds$i: no user registered"
13850                 [ -n "${cl_user2[mds$i]}" ] ||
13851                         error "mds$i: only ${cl_user1[mds$i]} is registered"
13852
13853                 user_rec1=$(changelog_user_rec mds$i ${cl_user1[mds$i]})
13854                 [ -n "$user_rec1" ] ||
13855                         error "mds$i: User ${cl_user1[mds$i]} not registered"
13856                 __changelog_clear mds$i ${cl_user1[mds$i]} +2
13857                 user_rec2=$(changelog_user_rec mds$i ${cl_user1[mds$i]})
13858                 [ -n "$user_rec2" ] ||
13859                         error "mds$i: User ${cl_user1[mds$i]} not registered"
13860                 echo "mds$i: verifying user ${cl_user1[mds$i]} clear: " \
13861                      "$user_rec1 + 2 == $user_rec2"
13862                 [ $((user_rec1 + 2)) == $user_rec2 ] ||
13863                         error "mds$i: user ${cl_user1[mds$i]} index expected " \
13864                               "$user_rec1 + 2, but is $user_rec2"
13865                 user_rec2=$(changelog_user_rec mds$i ${cl_user2[mds$i]})
13866                 [ -n "$user_rec2" ] ||
13867                         error "mds$i: User ${cl_user2[mds$i]} not registered"
13868                 [ $user_rec1 == $user_rec2 ] ||
13869                         error "mds$i: user ${cl_user2[mds$i]} index expected " \
13870                               "$user_rec1, but is $user_rec2"
13871         done
13872
13873         # ensure we are past the previous changelog_min_gc_interval set above
13874         sleep 2
13875
13876         # generate one more changelog to trigger fail_loc
13877         createmany -m $DIR/$tdir/${tfile}bis $((MDSCOUNT * 2)) ||
13878                 error "create $DIR/$tdir/${tfile}bis failed"
13879
13880         # ensure gc thread is done
13881         for i in $(mdts_nodes); do
13882                 wait_update $i \
13883                         "ps -e -o comm= | grep chlg_gc_thread" "" 20 ||
13884                         error "$i: GC-thread not done"
13885         done
13886
13887         local first_rec
13888         for i in $(seq $MDSCOUNT); do
13889                 # check cl_user1 still registered
13890                 changelog_users mds$i | grep -q "${cl_user1[mds$i]}" ||
13891                         error "mds$i: User ${cl_user1[mds$i]} not registered"
13892                 # check cl_user2 unregistered
13893                 changelog_users mds$i | grep -q "${cl_user2[mds$i]}" &&
13894                         error "mds$i: User ${cl_user2[mds$i]} still registered"
13895
13896                 # check changelogs are present and starting at $user_rec1 + 1
13897                 user_rec1=$(changelog_user_rec mds$i ${cl_user1[mds$i]})
13898                 [ -n "$user_rec1" ] ||
13899                         error "mds$i: User ${cl_user1[mds$i]} not registered"
13900                 first_rec=$($LFS changelog $(facet_svc mds$i) |
13901                             awk '{ print $1; exit; }')
13902
13903                 echo "mds$i: verifying first index $user_rec1 + 1 == $first_rec"
13904                 [ $((user_rec1 + 1)) == $first_rec ] ||
13905                         error "mds$i: first index should be $user_rec1 + 1, " \
13906                               "but is $first_rec"
13907         done
13908 }
13909 run_test 160g "changelog garbage collect (old users)"
13910
13911 test_160h() {
13912         remote_mds_nodsh && skip "remote MDS with nodsh" && return
13913         [[ $MDS1_VERSION -ge $(version_code 2.10.56) ]] ||
13914                 skip "Need MDS version at least 2.10.56"
13915
13916         local mdts=$(comma_list $(mdts_nodes))
13917
13918         # Create a user
13919         changelog_register || error "first changelog_register failed"
13920         changelog_register || error "second changelog_register failed"
13921         local cl_users
13922         declare -A cl_user1
13923         declare -A cl_user2
13924         local user_rec1
13925         local user_rec2
13926         local i
13927
13928         # generate some changelog records to accumulate on each MDT
13929         test_mkdir -c $MDSCOUNT $DIR/$tdir || error "test_mkdir $tdir failed"
13930         createmany -m $DIR/$tdir/$tfile $((MDSCOUNT * 2)) ||
13931                 error "create $DIR/$tdir/$tfile failed"
13932
13933         # check changelogs have been generated
13934         local nbcl=$(changelog_dump | wc -l)
13935         [[ $nbcl -eq 0 ]] && error "no changelogs found"
13936
13937         for param in "changelog_max_idle_time=10" \
13938                      "changelog_gc=1" \
13939                      "changelog_min_gc_interval=2"; do
13940                 local MDT0=$(facet_svc $SINGLEMDS)
13941                 local var="${param%=*}"
13942                 local old=$(do_facet mds1 "$LCTL get_param -n mdd.$MDT0.$var")
13943
13944                 stack_trap "do_nodes $mdts $LCTL set_param mdd.*.$var=$old" EXIT
13945                 do_nodes $mdts $LCTL set_param mdd.*.$param
13946         done
13947
13948         # force cl_user2 to be idle (1st part)
13949         sleep 9
13950
13951         for i in $(seq $MDSCOUNT); do
13952                 cl_users=(${CL_USERS[mds$i]})
13953                 cl_user1[mds$i]="${cl_users[0]}"
13954                 cl_user2[mds$i]="${cl_users[1]}"
13955
13956                 [ -n "${cl_user1[mds$i]}" ] ||
13957                         error "mds$i: no user registered"
13958                 [ -n "${cl_user2[mds$i]}" ] ||
13959                         error "mds$i: only ${cl_user2[mds$i]} is registered"
13960
13961                 user_rec1=$(changelog_user_rec mds$i ${cl_user1[mds$i]})
13962                 [ -n "$user_rec1" ] ||
13963                         error "mds$i: User ${cl_user1[mds$i]} not registered"
13964                 __changelog_clear mds$i ${cl_user1[mds$i]} +2
13965                 user_rec2=$(changelog_user_rec mds$i ${cl_user1[mds$i]})
13966                 [ -n "$user_rec2" ] ||
13967                         error "mds$i: User ${cl_user1[mds$i]} not registered"
13968                 echo "mds$i: verifying user ${cl_user1[mds$i]} clear: " \
13969                      "$user_rec1 + 2 == $user_rec2"
13970                 [ $((user_rec1 + 2)) == $user_rec2 ] ||
13971                         error "mds$i: user ${cl_user1[mds$i]} index expected " \
13972                               "$user_rec1 + 2, but is $user_rec2"
13973                 user_rec2=$(changelog_user_rec mds$i ${cl_user2[mds$i]})
13974                 [ -n "$user_rec2" ] ||
13975                         error "mds$i: User ${cl_user2[mds$i]} not registered"
13976                 [ $user_rec1 == $user_rec2 ] ||
13977                         error "mds$i: user ${cl_user2[mds$i]} index expected " \
13978                               "$user_rec1, but is $user_rec2"
13979         done
13980
13981         # force cl_user2 to be idle (2nd part) and to reach
13982         # changelog_max_idle_time
13983         sleep 2
13984
13985         # force each GC-thread start and block then
13986         # one per MDT/MDD, set fail_val accordingly
13987         #define OBD_FAIL_FORCE_GC_THREAD 0x1316
13988         do_nodes $mdts $LCTL set_param fail_loc=0x1316
13989
13990         # generate more changelogs to trigger fail_loc
13991         createmany -m $DIR/$tdir/${tfile}bis $((MDSCOUNT * 2)) ||
13992                 error "create $DIR/$tdir/${tfile}bis failed"
13993
13994         # stop MDT to stop GC-thread, should be done in back-ground as it will
13995         # block waiting for the thread to be released and exit
13996         declare -A stop_pids
13997         for i in $(seq $MDSCOUNT); do
13998                 stop mds$i &
13999                 stop_pids[mds$i]=$!
14000         done
14001
14002         for i in $(mdts_nodes); do
14003                 local facet
14004                 local nb=0
14005                 local facets=$(facets_up_on_host $i)
14006
14007                 for facet in ${facets//,/ }; do
14008                         if [[ $facet == mds* ]]; then
14009                                 nb=$((nb + 1))
14010                         fi
14011                 done
14012                 # ensure each MDS's gc threads are still present and all in "R"
14013                 # state (OBD_FAIL_FORCE_GC_THREAD effect!)
14014                 [[ $(do_node $i pgrep chlg_gc_thread | wc -l) -eq $nb ]] ||
14015                         error "$i: expected $nb GC-thread"
14016                 wait_update $i \
14017                         "ps -C chlg_gc_thread -o state --no-headers | uniq" \
14018                         "R" 20 ||
14019                         error "$i: GC-thread not found in R-state"
14020                 # check umounts of each MDT on MDS have reached kthread_stop()
14021                 [[ $(do_node $i pgrep umount | wc -l) -eq $nb ]] ||
14022                         error "$i: expected $nb umount"
14023                 wait_update $i \
14024                         "ps -C umount -o state --no-headers | uniq" "D" 20 ||
14025                         error "$i: umount not found in D-state"
14026         done
14027
14028         # release all GC-threads
14029         do_nodes $mdts $LCTL set_param fail_loc=0
14030
14031         # wait for MDT stop to complete
14032         for i in $(seq $MDSCOUNT); do
14033                 wait ${stop_pids[mds$i]} || error "mds$i: stop failed"
14034         done
14035
14036         # XXX
14037         # may try to check if any orphan changelog records are present
14038         # via ldiskfs/zfs and llog_reader...
14039
14040         # re-start/mount MDTs
14041         for i in $(seq $MDSCOUNT); do
14042                 start mds$i $(mdsdevname $i) $MDS_MOUNT_OPTS ||
14043                         error "Fail to start mds$i"
14044         done
14045
14046         local first_rec
14047         for i in $(seq $MDSCOUNT); do
14048                 # check cl_user1 still registered
14049                 changelog_users mds$i | grep -q "${cl_user1[mds$i]}" ||
14050                         error "mds$i: User ${cl_user1[mds$i]} not registered"
14051                 # check cl_user2 unregistered
14052                 changelog_users mds$i | grep -q "${cl_user2[mds$i]}" &&
14053                         error "mds$i: User ${cl_user2[mds$i]} still registered"
14054
14055                 # check changelogs are present and starting at $user_rec1 + 1
14056                 user_rec1=$(changelog_user_rec mds$i ${cl_user1[mds$i]})
14057                 [ -n "$user_rec1" ] ||
14058                         error "mds$i: User ${cl_user1[mds$i]} not registered"
14059                 first_rec=$($LFS changelog $(facet_svc mds$i) |
14060                             awk '{ print $1; exit; }')
14061
14062                 echo "mds$i: verifying first index $user_rec1 + 1 == $first_rec"
14063                 [ $((user_rec1 + 1)) == $first_rec ] ||
14064                         error "mds$i: first index should be $user_rec1 + 1, " \
14065                               "but is $first_rec"
14066         done
14067 }
14068 run_test 160h "changelog gc thread stop upon umount, orphan records delete " \
14069               "during mount"
14070
14071 test_160i() {
14072
14073         local mdts=$(comma_list $(mdts_nodes))
14074
14075         changelog_register || error "first changelog_register failed"
14076
14077         # generate some changelog records to accumulate on each MDT
14078         test_mkdir -c $MDSCOUNT $DIR/$tdir || error "mkdir $tdir failed"
14079         createmany -m $DIR/$tdir/$tfile $((MDSCOUNT * 2)) ||
14080                 error "create $DIR/$tdir/$tfile failed"
14081
14082         # check changelogs have been generated
14083         local nbcl=$(changelog_dump | wc -l)
14084         [[ $nbcl -eq 0 ]] && error "no changelogs found"
14085
14086         # simulate race between register and unregister
14087         # XXX as fail_loc is set per-MDS, with DNE configs the race
14088         # simulation will only occur for one MDT per MDS and for the
14089         # others the normal race scenario will take place
14090         #define CFS_FAIL_CHLOG_USER_REG_UNREG_RACE          0x1315
14091         do_nodes $mdts $LCTL set_param fail_loc=0x10001315
14092         do_nodes $mdts $LCTL set_param fail_val=1
14093
14094         # unregister 1st user
14095         changelog_deregister &
14096         local pid1=$!
14097         # wait some time for deregister work to reach race rdv
14098         sleep 2
14099         # register 2nd user
14100         changelog_register || error "2nd user register failed"
14101
14102         wait $pid1 || error "1st user deregister failed"
14103
14104         local i
14105         local last_rec
14106         declare -A LAST_REC
14107         for i in $(seq $MDSCOUNT); do
14108                 if changelog_users mds$i | grep "^cl"; then
14109                         # make sure new records are added with one user present
14110                         LAST_REC[mds$i]=$(changelog_users $SINGLEMDS |
14111                                           awk '/^current.index:/ { print $NF }')
14112                 else
14113                         error "mds$i has no user registered"
14114                 fi
14115         done
14116
14117         # generate more changelog records to accumulate on each MDT
14118         createmany -m $DIR/$tdir/${tfile}bis $((MDSCOUNT * 2)) ||
14119                 error "create $DIR/$tdir/${tfile}bis failed"
14120
14121         for i in $(seq $MDSCOUNT); do
14122                 last_rec=$(changelog_users $SINGLEMDS |
14123                            awk '/^current.index:/ { print $NF }')
14124                 echo "verify changelogs are on: $last_rec != ${LAST_REC[mds$i]}"
14125                 [ $last_rec != ${LAST_REC[mds$i]} ] ||
14126                         error "changelogs are off on mds$i"
14127         done
14128 }
14129 run_test 160i "changelog user register/unregister race"
14130
14131 test_160j() {
14132         remote_mds_nodsh && skip "remote MDS with nodsh"
14133         [[ $MDS1_VERSION -lt $(version_code 2.12.56) ]] &&
14134                 skip "Need MDS version at least 2.12.56"
14135
14136         mount_client $MOUNT2 || error "mount_client on $MOUNT2 failed"
14137
14138         changelog_register || error "first changelog_register failed"
14139
14140         # generate some changelog
14141         test_mkdir -c $MDSCOUNT $DIR/$tdir || error "mkdir $tdir failed"
14142         createmany -m $DIR/$tdir/${tfile}bis $((MDSCOUNT * 2)) ||
14143                 error "create $DIR/$tdir/${tfile}bis failed"
14144
14145         # open the changelog device
14146         exec 3>/dev/changelog-$FSNAME-MDT0000
14147         exec 4</dev/changelog-$FSNAME-MDT0000
14148
14149         # umount the first lustre mount
14150         umount $MOUNT
14151
14152         # read changelog
14153         cat <&4 >/dev/null || error "read changelog failed"
14154
14155         # clear changelog
14156         local cl_user="${CL_USERS[$SINGLEMDS]%% *}"
14157         changelog_users $SINGLEMDS | grep -q $cl_user ||
14158                 error "User $cl_user not found in changelog_users"
14159
14160         printf 'clear:'$cl_user':0' >&3
14161
14162         # close
14163         exec 3>&-
14164         exec 4<&-
14165
14166         # cleanup
14167         changelog_deregister || error "changelog_deregister failed"
14168
14169         umount $MOUNT2
14170         mount_client $MOUNT || error "mount_client on $MOUNT failed"
14171 }
14172 run_test 160j "client can be umounted  while its chanangelog is being used"
14173
14174 test_160k() {
14175         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14176         remote_mds_nodsh && skip "remote MDS with nodsh"
14177
14178         mkdir -p $DIR/$tdir/1/1
14179
14180         changelog_register || error "changelog_register failed"
14181         local cl_user="${CL_USERS[$SINGLEMDS]%% *}"
14182
14183         changelog_users $SINGLEMDS | grep -q $cl_user ||
14184                 error "User '$cl_user' not found in changelog_users"
14185 #define OBD_FAIL_MDS_CHANGELOG_REORDER 0x15d
14186         do_facet mds1 $LCTL set_param fail_loc=0x8000015d fail_val=3
14187         rmdir $DIR/$tdir/1/1 & sleep 1
14188         mkdir $DIR/$tdir/2
14189         touch $DIR/$tdir/2/2
14190         rm -rf $DIR/$tdir/2
14191
14192         wait
14193         sleep 4
14194
14195         changelog_dump | grep rmdir || error "rmdir not recorded"
14196
14197         rm -rf $DIR/$tdir
14198         changelog_deregister
14199 }
14200 run_test 160k "Verify that changelog records are not lost"
14201
14202 test_161a() {
14203         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14204
14205         test_mkdir -c1 $DIR/$tdir
14206         cp /etc/hosts $DIR/$tdir/$tfile
14207         test_mkdir -c1 $DIR/$tdir/foo1
14208         test_mkdir -c1 $DIR/$tdir/foo2
14209         ln $DIR/$tdir/$tfile $DIR/$tdir/foo1/sofia
14210         ln $DIR/$tdir/$tfile $DIR/$tdir/foo2/zachary
14211         ln $DIR/$tdir/$tfile $DIR/$tdir/foo1/luna
14212         ln $DIR/$tdir/$tfile $DIR/$tdir/foo2/thor
14213         local FID=$($LFS path2fid $DIR/$tdir/$tfile | tr -d '[]')
14214         if [ "$($LFS fid2path $DIR $FID | wc -l)" != "5" ]; then
14215                 $LFS fid2path $DIR $FID
14216                 error "bad link ea"
14217         fi
14218         # middle
14219         rm $DIR/$tdir/foo2/zachary
14220         # last
14221         rm $DIR/$tdir/foo2/thor
14222         # first
14223         rm $DIR/$tdir/$tfile
14224         # rename
14225         mv $DIR/$tdir/foo1/sofia $DIR/$tdir/foo2/maggie
14226         [ "$($LFS fid2path $FSNAME --link 1 $FID)" != "$tdir/foo2/maggie" ] &&
14227                 { $LFS fid2path $DIR $FID; error "bad link rename"; }
14228         rm $DIR/$tdir/foo2/maggie
14229
14230         # overflow the EA
14231         local longname=$tfile.avg_len_is_thirty_two_
14232         stack_trap "unlinkmany $DIR/$tdir/foo2/$longname 1000 || \
14233                 error_noexit 'failed to unlink many hardlinks'" EXIT
14234         createmany -l$DIR/$tdir/foo1/luna $DIR/$tdir/foo2/$longname 1000 ||
14235                 error "failed to hardlink many files"
14236         links=$($LFS fid2path $DIR $FID | wc -l)
14237         echo -n "${links}/1000 links in link EA"
14238         [[ $links -gt 60 ]] || error "expected at least 60 links in link EA"
14239 }
14240 run_test 161a "link ea sanity"
14241
14242 test_161b() {
14243         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14244         [ $MDSCOUNT -lt 2 ] && skip_env "skipping remote directory test"
14245
14246         local MDTIDX=1
14247         local remote_dir=$DIR/$tdir/remote_dir
14248
14249         mkdir -p $DIR/$tdir
14250         $LFS mkdir -i $MDTIDX $remote_dir ||
14251                 error "create remote directory failed"
14252
14253         cp /etc/hosts $remote_dir/$tfile
14254         mkdir -p $remote_dir/foo1
14255         mkdir -p $remote_dir/foo2
14256         ln $remote_dir/$tfile $remote_dir/foo1/sofia
14257         ln $remote_dir/$tfile $remote_dir/foo2/zachary
14258         ln $remote_dir/$tfile $remote_dir/foo1/luna
14259         ln $remote_dir/$tfile $remote_dir/foo2/thor
14260
14261         local FID=$($LFS path2fid $remote_dir/$tfile | tr -d '[' |
14262                      tr -d ']')
14263         if [ "$($LFS fid2path $DIR $FID | wc -l)" != "5" ]; then
14264                 $LFS fid2path $DIR $FID
14265                 error "bad link ea"
14266         fi
14267         # middle
14268         rm $remote_dir/foo2/zachary
14269         # last
14270         rm $remote_dir/foo2/thor
14271         # first
14272         rm $remote_dir/$tfile
14273         # rename
14274         mv $remote_dir/foo1/sofia $remote_dir/foo2/maggie
14275         local link_path=$($LFS fid2path $FSNAME --link 1 $FID)
14276         if [ "$DIR/$link_path" != "$remote_dir/foo2/maggie" ]; then
14277                 $LFS fid2path $DIR $FID
14278                 error "bad link rename"
14279         fi
14280         rm $remote_dir/foo2/maggie
14281
14282         # overflow the EA
14283         local longname=filename_avg_len_is_thirty_two_
14284         createmany -l$remote_dir/foo1/luna $remote_dir/foo2/$longname 1000 ||
14285                 error "failed to hardlink many files"
14286         links=$($LFS fid2path $DIR $FID | wc -l)
14287         echo -n "${links}/1000 links in link EA"
14288         [[ ${links} -gt 60 ]] ||
14289                 error "expected at least 60 links in link EA"
14290         unlinkmany $remote_dir/foo2/$longname 1000 ||
14291         error "failed to unlink many hardlinks"
14292 }
14293 run_test 161b "link ea sanity under remote directory"
14294
14295 test_161c() {
14296         remote_mds_nodsh && skip "remote MDS with nodsh"
14297         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14298         [[ $MDS1_VERSION -lt $(version_code 2.1.5) ]] &&
14299                 skip "Need MDS version at least 2.1.5"
14300
14301         # define CLF_RENAME_LAST 0x0001
14302         # rename overwrite a target having nlink = 1 (changelog flag 0x1)
14303         changelog_register || error "changelog_register failed"
14304
14305         rm -rf $DIR/$tdir
14306         test_mkdir -i $((MDSCOUNT - 1)) $DIR/$tdir
14307         touch $DIR/$tdir/foo_161c
14308         touch $DIR/$tdir/bar_161c
14309         mv -f $DIR/$tdir/foo_161c $DIR/$tdir/bar_161c
14310         changelog_dump | grep RENME | tail -n 5
14311         local flags=$(changelog_dump | grep "RENME.*bar_161c" | cut -f5 -d' ')
14312         changelog_clear 0 || error "changelog_clear failed"
14313         if [ x$flags != "x0x1" ]; then
14314                 error "flag $flags is not 0x1"
14315         fi
14316
14317         echo "rename overwrite target with nlink = 1, changelog flags=$flags"
14318         # rename overwrite a target having nlink > 1 (changelog flag 0x0)
14319         touch $DIR/$tdir/foo_161c
14320         touch $DIR/$tdir/bar_161c
14321         ln $DIR/$tdir/bar_161c $DIR/$tdir/foobar_161c
14322         mv -f $DIR/$tdir/foo_161c $DIR/$tdir/bar_161c
14323         changelog_dump | grep RENME | tail -n 5
14324         flags=$(changelog_dump | grep "RENME.*bar_161c" | cut -f5 -d' ')
14325         changelog_clear 0 || error "changelog_clear failed"
14326         if [ x$flags != "x0x0" ]; then
14327                 error "flag $flags is not 0x0"
14328         fi
14329         echo "rename overwrite a target having nlink > 1," \
14330                 "changelog record has flags of $flags"
14331
14332         # rename doesn't overwrite a target (changelog flag 0x0)
14333         touch $DIR/$tdir/foo_161c
14334         mv -f $DIR/$tdir/foo_161c $DIR/$tdir/foo2_161c
14335         changelog_dump | grep RENME | tail -n 5
14336         flags=$(changelog_dump | grep RENME | tail -1 | cut -f5 -d' ')
14337         changelog_clear 0 || error "changelog_clear failed"
14338         if [ x$flags != "x0x0" ]; then
14339                 error "flag $flags is not 0x0"
14340         fi
14341         echo "rename doesn't overwrite a target," \
14342                 "changelog record has flags of $flags"
14343
14344         # define CLF_UNLINK_LAST 0x0001
14345         # unlink a file having nlink = 1 (changelog flag 0x1)
14346         rm -f $DIR/$tdir/foo2_161c
14347         changelog_dump | grep UNLNK | tail -n 5
14348         flags=$(changelog_dump | grep UNLNK | tail -1 | cut -f5 -d' ')
14349         changelog_clear 0 || error "changelog_clear failed"
14350         if [ x$flags != "x0x1" ]; then
14351                 error "flag $flags is not 0x1"
14352         fi
14353         echo "unlink a file having nlink = 1," \
14354                 "changelog record has flags of $flags"
14355
14356         # unlink a file having nlink > 1 (changelog flag 0x0)
14357         ln -f $DIR/$tdir/bar_161c $DIR/$tdir/foobar_161c
14358         rm -f $DIR/$tdir/foobar_161c
14359         changelog_dump | grep UNLNK | tail -n 5
14360         flags=$(changelog_dump | grep UNLNK | tail -1 | cut -f5 -d' ')
14361         changelog_clear 0 || error "changelog_clear failed"
14362         if [ x$flags != "x0x0" ]; then
14363                 error "flag $flags is not 0x0"
14364         fi
14365         echo "unlink a file having nlink > 1, changelog record flags '$flags'"
14366 }
14367 run_test 161c "check CL_RENME[UNLINK] changelog record flags"
14368
14369 test_161d() {
14370         remote_mds_nodsh && skip "remote MDS with nodsh"
14371         [ -n "$FILESET" ] && skip "Not functional for FILESET set"
14372
14373         local pid
14374         local fid
14375
14376         changelog_register || error "changelog_register failed"
14377
14378         # work in a standalone dir to avoid locking on $DIR/$MOUNT to
14379         # interfer with $MOUNT/.lustre/fid/ access
14380         mkdir $DIR/$tdir
14381         [[ $? -eq 0 ]] || error "mkdir failed"
14382
14383         #define OBD_FAIL_LLITE_CREATE_NODE_PAUSE 0x140c | OBD_FAIL_ONCE
14384         $LCTL set_param fail_loc=0x8000140c
14385         # 5s pause
14386         $LCTL set_param fail_val=5
14387
14388         # create file
14389         echo foofoo > $DIR/$tdir/$tfile &
14390         pid=$!
14391
14392         # wait for create to be delayed
14393         sleep 2
14394
14395         ps -p $pid
14396         [[ $? -eq 0 ]] || error "create should be blocked"
14397
14398         local tempfile="$(mktemp --tmpdir $tfile.XXXXXX)"
14399         stack_trap "rm -f $tempfile"
14400         fid=$(changelog_extract_field "CREAT" "$tfile" "t=")
14401         cat $MOUNT/.lustre/fid/$fid 2>/dev/null >$tempfile || error "cat failed"
14402         # some delay may occur during ChangeLog publishing and file read just
14403         # above, that could allow file write to happen finally
14404         [[ -s $tempfile ]] && echo "file should be empty"
14405
14406         $LCTL set_param fail_loc=0
14407
14408         wait $pid
14409         [[ $? -eq 0 ]] || error "create failed"
14410 }
14411 run_test 161d "create with concurrent .lustre/fid access"
14412
14413 check_path() {
14414         local expected="$1"
14415         shift
14416         local fid="$2"
14417
14418         local path
14419         path=$($LFS fid2path "$@")
14420         local rc=$?
14421
14422         if [ $rc -ne 0 ]; then
14423                 error "path looked up of '$expected' failed: rc=$rc"
14424         elif [ "$path" != "$expected" ]; then
14425                 error "path looked up '$path' instead of '$expected'"
14426         else
14427                 echo "FID '$fid' resolves to path '$path' as expected"
14428         fi
14429 }
14430
14431 test_162a() { # was test_162
14432         test_mkdir -p -c1 $DIR/$tdir/d2
14433         touch $DIR/$tdir/d2/$tfile
14434         touch $DIR/$tdir/d2/x1
14435         touch $DIR/$tdir/d2/x2
14436         test_mkdir -p -c1 $DIR/$tdir/d2/a/b/c
14437         test_mkdir -p -c1 $DIR/$tdir/d2/p/q/r
14438         # regular file
14439         local fid=$($LFS path2fid $DIR/$tdir/d2/$tfile | tr -d '[]')
14440         check_path "$tdir/d2/$tfile" $FSNAME "$fid" --link 0
14441
14442         # softlink
14443         ln -s $DIR/$tdir/d2/$tfile $DIR/$tdir/d2/p/q/r/slink
14444         fid=$($LFS path2fid $DIR/$tdir/d2/p/q/r/slink | tr -d '[]')
14445         check_path "$tdir/d2/p/q/r/slink" $FSNAME "$fid" --link 0
14446
14447         # softlink to wrong file
14448         ln -s /this/is/garbage $DIR/$tdir/d2/p/q/r/slink.wrong
14449         fid=$($LFS path2fid $DIR/$tdir/d2/p/q/r/slink.wrong | tr -d '[]')
14450         check_path "$tdir/d2/p/q/r/slink.wrong" $FSNAME "$fid" --link 0
14451
14452         # hardlink
14453         ln $DIR/$tdir/d2/$tfile $DIR/$tdir/d2/p/q/r/hlink
14454         mv $DIR/$tdir/d2/$tfile $DIR/$tdir/d2/a/b/c/new_file
14455         fid=$($LFS path2fid $DIR/$tdir/d2/a/b/c/new_file | tr -d '[]')
14456         # fid2path dir/fsname should both work
14457         check_path "$tdir/d2/a/b/c/new_file" $FSNAME "$fid" --link 1
14458         check_path "$DIR/$tdir/d2/p/q/r/hlink" $DIR "$fid" --link 0
14459
14460         # hardlink count: check that there are 2 links
14461         local nlinks=$($LFS fid2path $DIR "$fid" | wc -l)
14462         [ $nlinks -eq 2 ] || error "expect 2 links, found $nlinks"
14463
14464         # hardlink indexing: remove the first link
14465         rm $DIR/$tdir/d2/p/q/r/hlink
14466         check_path "$tdir/d2/a/b/c/new_file" $FSNAME $fid --link 0
14467 }
14468 run_test 162a "path lookup sanity"
14469
14470 test_162b() {
14471         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14472         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
14473
14474         mkdir $DIR/$tdir
14475         $LFS setdirstripe -i0 -c$MDSCOUNT -H all_char $DIR/$tdir/striped_dir ||
14476                                 error "create striped dir failed"
14477
14478         local FID=$($LFS getdirstripe $DIR/$tdir/striped_dir |
14479                                         tail -n 1 | awk '{print $2}')
14480         stat $MOUNT/.lustre/fid/$FID && error "sub_stripe can be accessed"
14481
14482         touch $DIR/$tdir/striped_dir/f{0..4} || error "touch f0..4 failed"
14483         mkdir $DIR/$tdir/striped_dir/d{0..4} || error "mkdir d0..4 failed"
14484
14485         # regular file
14486         for ((i=0;i<5;i++)); do
14487                 FID=$($LFS path2fid $DIR/$tdir/striped_dir/f$i | tr -d '[]') ||
14488                         error "get fid for f$i failed"
14489                 check_path "$tdir/striped_dir/f$i" $FSNAME $FID --link 0
14490
14491                 FID=$($LFS path2fid $DIR/$tdir/striped_dir/d$i | tr -d '[]') ||
14492                         error "get fid for d$i failed"
14493                 check_path "$tdir/striped_dir/d$i" $FSNAME $FID --link 0
14494         done
14495
14496         return 0
14497 }
14498 run_test 162b "striped directory path lookup sanity"
14499
14500 # LU-4239: Verify fid2path works with paths 100 or more directories deep
14501 test_162c() {
14502         [[ $MDS1_VERSION -lt $(version_code 2.7.51) ]] &&
14503                 skip "Need MDS version at least 2.7.51"
14504
14505         local lpath=$tdir.local
14506         local rpath=$tdir.remote
14507
14508         test_mkdir $DIR/$lpath
14509         test_mkdir $DIR/$rpath
14510
14511         for ((i = 0; i <= 101; i++)); do
14512                 lpath="$lpath/$i"
14513                 mkdir $DIR/$lpath
14514                 FID=$($LFS path2fid $DIR/$lpath | tr -d '[]') ||
14515                         error "get fid for local directory $DIR/$lpath failed"
14516                 check_path "$DIR/$lpath" $MOUNT $FID --link 0
14517
14518                 rpath="$rpath/$i"
14519                 test_mkdir $DIR/$rpath
14520                 FID=$($LFS path2fid $DIR/$rpath | tr -d '[]') ||
14521                         error "get fid for remote directory $DIR/$rpath failed"
14522                 check_path "$DIR/$rpath" $MOUNT $FID --link 0
14523         done
14524
14525         return 0
14526 }
14527 run_test 162c "fid2path works with paths 100 or more directories deep"
14528
14529 test_169() {
14530         # do directio so as not to populate the page cache
14531         log "creating a 10 Mb file"
14532         $MULTIOP $DIR/$tfile oO_CREAT:O_DIRECT:O_RDWR:w$((10*1048576))c || error "multiop failed while creating a file"
14533         log "starting reads"
14534         dd if=$DIR/$tfile of=/dev/null bs=4096 &
14535         log "truncating the file"
14536         $MULTIOP $DIR/$tfile oO_TRUNC:c || error "multiop failed while truncating the file"
14537         log "killing dd"
14538         kill %+ || true # reads might have finished
14539         echo "wait until dd is finished"
14540         wait
14541         log "removing the temporary file"
14542         rm -rf $DIR/$tfile || error "tmp file removal failed"
14543 }
14544 run_test 169 "parallel read and truncate should not deadlock"
14545
14546 test_170() {
14547         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14548
14549         $LCTL clear     # bug 18514
14550         $LCTL debug_daemon start $TMP/${tfile}_log_good
14551         touch $DIR/$tfile
14552         $LCTL debug_daemon stop
14553         sed -e "s/^...../a/g" $TMP/${tfile}_log_good > $TMP/${tfile}_log_bad ||
14554                 error "sed failed to read log_good"
14555
14556         $LCTL debug_daemon start $TMP/${tfile}_log_good
14557         rm -rf $DIR/$tfile
14558         $LCTL debug_daemon stop
14559
14560         $LCTL df $TMP/${tfile}_log_bad > $TMP/${tfile}_log_bad.out 2>&1 ||
14561                error "lctl df log_bad failed"
14562
14563         local bad_line=$(tail -n 1 $TMP/${tfile}_log_bad.out | awk '{print $9}')
14564         local good_line1=$(tail -n 1 $TMP/${tfile}_log_bad.out | awk '{print $5}')
14565
14566         $LCTL df $TMP/${tfile}_log_good > $TMP/${tfile}_log_good.out 2>&1
14567         local good_line2=$(tail -n 1 $TMP/${tfile}_log_good.out | awk '{print $5}')
14568
14569         [ "$bad_line" ] && [ "$good_line1" ] && [ "$good_line2" ] ||
14570                 error "bad_line good_line1 good_line2 are empty"
14571
14572         cat $TMP/${tfile}_log_good >> $TMP/${tfile}_logs_corrupt
14573         cat $TMP/${tfile}_log_bad >> $TMP/${tfile}_logs_corrupt
14574         cat $TMP/${tfile}_log_good >> $TMP/${tfile}_logs_corrupt
14575
14576         $LCTL df $TMP/${tfile}_logs_corrupt > $TMP/${tfile}_log_bad.out 2>&1
14577         local bad_line_new=$(tail -n 1 $TMP/${tfile}_log_bad.out | awk '{print $9}')
14578         local good_line_new=$(tail -n 1 $TMP/${tfile}_log_bad.out | awk '{print $5}')
14579
14580         [ "$bad_line_new" ] && [ "$good_line_new" ] ||
14581                 error "bad_line_new good_line_new are empty"
14582
14583         local expected_good=$((good_line1 + good_line2*2))
14584
14585         rm -f $TMP/${tfile}*
14586         # LU-231, short malformed line may not be counted into bad lines
14587         if [ $bad_line -ne $bad_line_new ] &&
14588                    [ $bad_line -ne $((bad_line_new - 1)) ]; then
14589                 error "expected $bad_line bad lines, but got $bad_line_new"
14590                 return 1
14591         fi
14592
14593         if [ $expected_good -ne $good_line_new ]; then
14594                 error "expected $expected_good good lines, but got $good_line_new"
14595                 return 2
14596         fi
14597         true
14598 }
14599 run_test 170 "test lctl df to handle corrupted log ====================="
14600
14601 test_171() { # bug20592
14602         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14603
14604         #define OBD_FAIL_PTLRPC_DUMP_LOG         0x50e
14605         $LCTL set_param fail_loc=0x50e
14606         $LCTL set_param fail_val=3000
14607         multiop_bg_pause $DIR/$tfile O_s || true
14608         local MULTIPID=$!
14609         kill -USR1 $MULTIPID
14610         # cause log dump
14611         sleep 3
14612         wait $MULTIPID
14613         if dmesg | grep "recursive fault"; then
14614                 error "caught a recursive fault"
14615         fi
14616         $LCTL set_param fail_loc=0
14617         true
14618 }
14619 run_test 171 "test libcfs_debug_dumplog_thread stuck in do_exit() ======"
14620
14621 # it would be good to share it with obdfilter-survey/iokit-libecho code
14622 setup_obdecho_osc () {
14623         local rc=0
14624         local ost_nid=$1
14625         local obdfilter_name=$2
14626         echo "Creating new osc for $obdfilter_name on $ost_nid"
14627         # make sure we can find loopback nid
14628         $LCTL add_uuid $ost_nid $ost_nid >/dev/null 2>&1
14629
14630         [ $rc -eq 0 ] && { $LCTL attach osc ${obdfilter_name}_osc     \
14631                            ${obdfilter_name}_osc_UUID || rc=2; }
14632         [ $rc -eq 0 ] && { $LCTL --device ${obdfilter_name}_osc setup \
14633                            ${obdfilter_name}_UUID  $ost_nid || rc=3; }
14634         return $rc
14635 }
14636
14637 cleanup_obdecho_osc () {
14638         local obdfilter_name=$1
14639         $LCTL --device ${obdfilter_name}_osc cleanup >/dev/null
14640         $LCTL --device ${obdfilter_name}_osc detach  >/dev/null
14641         return 0
14642 }
14643
14644 obdecho_test() {
14645         local OBD=$1
14646         local node=$2
14647         local pages=${3:-64}
14648         local rc=0
14649         local id
14650
14651         local count=10
14652         local obd_size=$(get_obd_size $node $OBD)
14653         local page_size=$(get_page_size $node)
14654         if [[ -n "$obd_size" ]]; then
14655                 local new_count=$((obd_size / (pages * page_size / 1024)))
14656                 [[ $new_count -ge $count ]] || count=$new_count
14657         fi
14658
14659         do_facet $node "$LCTL attach echo_client ec ec_uuid" || rc=1
14660         [ $rc -eq 0 ] && { do_facet $node "$LCTL --device ec setup $OBD" ||
14661                            rc=2; }
14662         if [ $rc -eq 0 ]; then
14663             id=$(do_facet $node "$LCTL --device ec create 1"  | awk '/object id/ {print $6}')
14664             [ ${PIPESTATUS[0]} -eq 0 -a -n "$id" ] || rc=3
14665         fi
14666         echo "New object id is $id"
14667         [ $rc -eq 0 ] && { do_facet $node "$LCTL --device ec getattr $id" ||
14668                            rc=4; }
14669         [ $rc -eq 0 ] && { do_facet $node "$LCTL --device ec "                 \
14670                            "test_brw $count w v $pages $id" || rc=4; }
14671         [ $rc -eq 0 ] && { do_facet $node "$LCTL --device ec destroy $id 1" ||
14672                            rc=4; }
14673         [ $rc -eq 0 ] || [ $rc -gt 2 ] &&
14674                 { do_facet $node "$LCTL --device ec cleanup" || rc=5; }
14675         [ $rc -eq 0 ] || [ $rc -gt 1 ] &&
14676                 { do_facet $node "$LCTL --device ec detach" || rc=6; }
14677         [ $rc -ne 0 ] && echo "obecho_create_test failed: $rc"
14678         return $rc
14679 }
14680
14681 test_180a() {
14682         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14683
14684         if ! module_loaded obdecho; then
14685                 load_module obdecho/obdecho &&
14686                         stack_trap "rmmod obdecho" EXIT ||
14687                         error "unable to load obdecho on client"
14688         fi
14689
14690         local osc=$($LCTL dl | grep -v mdt | awk '$3 == "osc" {print $4; exit}')
14691         local host=$($LCTL get_param -n osc.$osc.import |
14692                      awk '/current_connection:/ { print $2 }' )
14693         local target=$($LCTL get_param -n osc.$osc.import |
14694                        awk '/target:/ { print $2 }' )
14695         target=${target%_UUID}
14696
14697         if [ -n "$target" ]; then
14698                 setup_obdecho_osc $host $target &&
14699                         stack_trap "cleanup_obdecho_osc $target" EXIT ||
14700                         { error "obdecho setup failed with $?"; return; }
14701
14702                 obdecho_test ${target}_osc client ||
14703                         error "obdecho_test failed on ${target}_osc"
14704         else
14705                 $LCTL get_param osc.$osc.import
14706                 error "there is no osc.$osc.import target"
14707         fi
14708 }
14709 run_test 180a "test obdecho on osc"
14710
14711 test_180b() {
14712         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14713         remote_ost_nodsh && skip "remote OST with nodsh"
14714
14715         do_rpc_nodes $(facet_active_host ost1) load_module obdecho/obdecho &&
14716                 stack_trap "do_facet ost1 rmmod obdecho" EXIT ||
14717                 error "failed to load module obdecho"
14718
14719         local target=$(do_facet ost1 $LCTL dl |
14720                        awk '/obdfilter/ { print $4; exit; }')
14721
14722         if [ -n "$target" ]; then
14723                 obdecho_test $target ost1 || error "obdecho_test failed with $?"
14724         else
14725                 do_facet ost1 $LCTL dl
14726                 error "there is no obdfilter target on ost1"
14727         fi
14728 }
14729 run_test 180b "test obdecho directly on obdfilter"
14730
14731 test_180c() { # LU-2598
14732         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14733         remote_ost_nodsh && skip "remote OST with nodsh"
14734         [[ $MDS1_VERSION -lt $(version_code 2.4.0) ]] &&
14735                 skip "Need MDS version at least 2.4.0"
14736
14737         do_rpc_nodes $(facet_active_host ost1) load_module obdecho/obdecho &&
14738                 stack_trap "do_facet ost1 rmmod obdecho" EXIT ||
14739                 error "failed to load module obdecho"
14740
14741         local target=$(do_facet ost1 $LCTL dl |
14742                        awk '/obdfilter/ { print $4; exit; }')
14743
14744         if [ -n "$target" ]; then
14745                 local pages=16384 # 64MB bulk I/O RPC size
14746
14747                 obdecho_test "$target" ost1 "$pages" ||
14748                         error "obdecho_test with pages=$pages failed with $?"
14749         else
14750                 do_facet ost1 $LCTL dl
14751                 error "there is no obdfilter target on ost1"
14752         fi
14753 }
14754 run_test 180c "test huge bulk I/O size on obdfilter, don't LASSERT"
14755
14756 test_181() { # bug 22177
14757         test_mkdir $DIR/$tdir
14758         # create enough files to index the directory
14759         createmany -o $DIR/$tdir/foobar 4000
14760         # print attributes for debug purpose
14761         lsattr -d .
14762         # open dir
14763         multiop_bg_pause $DIR/$tdir D_Sc || return 1
14764         MULTIPID=$!
14765         # remove the files & current working dir
14766         unlinkmany $DIR/$tdir/foobar 4000
14767         rmdir $DIR/$tdir
14768         kill -USR1 $MULTIPID
14769         wait $MULTIPID
14770         stat $DIR/$tdir && error "open-unlinked dir was not removed!"
14771         return 0
14772 }
14773 run_test 181 "Test open-unlinked dir ========================"
14774
14775 test_182() {
14776         local fcount=1000
14777         local tcount=10
14778
14779         mkdir -p $DIR/$tdir || error "creating dir $DIR/$tdir"
14780
14781         $LCTL set_param mdc.*.rpc_stats=clear
14782
14783         for (( i = 0; i < $tcount; i++ )) ; do
14784                 mkdir $DIR/$tdir/$i
14785         done
14786
14787         for (( i = 0; i < $tcount; i++ )) ; do
14788                 createmany -o $DIR/$tdir/$i/f- $fcount &
14789         done
14790         wait
14791
14792         for (( i = 0; i < $tcount; i++ )) ; do
14793                 unlinkmany $DIR/$tdir/$i/f- $fcount &
14794         done
14795         wait
14796
14797         $LCTL get_param mdc.*.rpc_stats
14798
14799         rm -rf $DIR/$tdir
14800 }
14801 run_test 182 "Test parallel modify metadata operations ================"
14802
14803 test_183() { # LU-2275
14804         [ $PARALLEL == "yes" ] && skip "skip parallel run"
14805         remote_mds_nodsh && skip "remote MDS with nodsh"
14806         [[ $MDS1_VERSION -lt $(version_code 2.3.56) ]] &&
14807                 skip "Need MDS version at least 2.3.56"
14808
14809         mkdir -p $DIR/$tdir || error "creating dir $DIR/$tdir"
14810         echo aaa > $DIR/$tdir/$tfile
14811
14812 #define OBD_FAIL_MDS_NEGATIVE_POSITIVE  0x148
14813         do_facet $SINGLEMDS $LCTL set_param fail_loc=0x148
14814
14815         ls -l $DIR/$tdir && error "ls succeeded, should have failed"
14816         cat $DIR/$tdir/$tfile && error "cat succeeded, should have failed"
14817
14818         do_facet $SINGLEMDS $LCTL set_param fail_loc=0
14819
14820         # Flush negative dentry cache
14821         touch $DIR/$tdir/$tfile
14822
14823         # We are not checking for any leaked references here, they'll
14824         # become evident next time we do cleanup with module unload.
14825         rm -rf $DIR/$tdir
14826 }
14827 run_test 183 "No crash or request leak in case of strange dispositions ========"
14828
14829 # test suite 184 is for LU-2016, LU-2017
14830 test_184a() {
14831         check_swap_layouts_support
14832
14833         dir0=$DIR/$tdir/$testnum
14834         test_mkdir -p -c1 $dir0
14835         ref1=/etc/passwd
14836         ref2=/etc/group
14837         file1=$dir0/f1
14838         file2=$dir0/f2
14839         $LFS setstripe -c1 $file1
14840         cp $ref1 $file1
14841         $LFS setstripe -c2 $file2
14842         cp $ref2 $file2
14843         gen1=$($LFS getstripe -g $file1)
14844         gen2=$($LFS getstripe -g $file2)
14845
14846         $LFS swap_layouts $file1 $file2 || error "swap of file layout failed"
14847         gen=$($LFS getstripe -g $file1)
14848         [[ $gen1 != $gen ]] ||
14849                 "Layout generation on $file1 does not change"
14850         gen=$($LFS getstripe -g $file2)
14851         [[ $gen2 != $gen ]] ||
14852                 "Layout generation on $file2 does not change"
14853
14854         cmp $ref1 $file2 || error "content compare failed ($ref1 != $file2)"
14855         cmp $ref2 $file1 || error "content compare failed ($ref2 != $file1)"
14856
14857         lfsck_verify_pfid $file1 $file2 || error "PFID are not transferred"
14858 }
14859 run_test 184a "Basic layout swap"
14860
14861 test_184b() {
14862         check_swap_layouts_support
14863
14864         dir0=$DIR/$tdir/$testnum
14865         mkdir -p $dir0 || error "creating dir $dir0"
14866         file1=$dir0/f1
14867         file2=$dir0/f2
14868         file3=$dir0/f3
14869         dir1=$dir0/d1
14870         dir2=$dir0/d2
14871         mkdir $dir1 $dir2
14872         $LFS setstripe -c1 $file1
14873         $LFS setstripe -c2 $file2
14874         $LFS setstripe -c1 $file3
14875         chown $RUNAS_ID $file3
14876         gen1=$($LFS getstripe -g $file1)
14877         gen2=$($LFS getstripe -g $file2)
14878
14879         $LFS swap_layouts $dir1 $dir2 &&
14880                 error "swap of directories layouts should fail"
14881         $LFS swap_layouts $dir1 $file1 &&
14882                 error "swap of directory and file layouts should fail"
14883         $RUNAS $LFS swap_layouts $file1 $file2 &&
14884                 error "swap of file we cannot write should fail"
14885         $LFS swap_layouts $file1 $file3 &&
14886                 error "swap of file with different owner should fail"
14887         /bin/true # to clear error code
14888 }
14889 run_test 184b "Forbidden layout swap (will generate errors)"
14890
14891 test_184c() {
14892         local cmpn_arg=$(cmp -n 2>&1 | grep "invalid option")
14893         [ -n "$cmpn_arg" ] && skip_env "cmp does not support -n"
14894         check_swap_layouts_support
14895
14896         local dir0=$DIR/$tdir/$testnum
14897         mkdir -p $dir0 || error "creating dir $dir0"
14898
14899         local ref1=$dir0/ref1
14900         local ref2=$dir0/ref2
14901         local file1=$dir0/file1
14902         local file2=$dir0/file2
14903         # create a file large enough for the concurrent test
14904         dd if=/dev/urandom of=$ref1 bs=1M count=$((RANDOM % 50 + 20))
14905         dd if=/dev/urandom of=$ref2 bs=1M count=$((RANDOM % 50 + 20))
14906         echo "ref file size: ref1($(stat -c %s $ref1))," \
14907              "ref2($(stat -c %s $ref2))"
14908
14909         cp $ref2 $file2
14910         dd if=$ref1 of=$file1 bs=16k &
14911         local DD_PID=$!
14912
14913         # Make sure dd starts to copy file
14914         while [ ! -f $file1 ]; do sleep 0.1; done
14915
14916         $LFS swap_layouts $file1 $file2
14917         local rc=$?
14918         wait $DD_PID
14919         [[ $? == 0 ]] || error "concurrent write on $file1 failed"
14920         [[ $rc == 0 ]] || error "swap of $file1 and $file2 failed"
14921
14922         # how many bytes copied before swapping layout
14923         local copied=$(stat -c %s $file2)
14924         local remaining=$(stat -c %s $ref1)
14925         remaining=$((remaining - copied))
14926         echo "Copied $copied bytes before swapping layout..."
14927
14928         cmp -n $copied $file1 $ref2 | grep differ &&
14929                 error "Content mismatch [0, $copied) of ref2 and file1"
14930         cmp -n $copied $file2 $ref1 ||
14931                 error "Content mismatch [0, $copied) of ref1 and file2"
14932         cmp -i $copied:$copied -n $remaining $file1 $ref1 ||
14933                 error "Content mismatch [$copied, EOF) of ref1 and file1"
14934
14935         # clean up
14936         rm -f $ref1 $ref2 $file1 $file2
14937 }
14938 run_test 184c "Concurrent write and layout swap"
14939
14940 test_184d() {
14941         check_swap_layouts_support
14942         [ -z "$(which getfattr 2>/dev/null)" ] &&
14943                 skip_env "no getfattr command"
14944
14945         local file1=$DIR/$tdir/$tfile-1
14946         local file2=$DIR/$tdir/$tfile-2
14947         local file3=$DIR/$tdir/$tfile-3
14948         local lovea1
14949         local lovea2
14950
14951         mkdir -p $DIR/$tdir
14952         touch $file1 || error "create $file1 failed"
14953         $OPENFILE -f O_CREAT:O_LOV_DELAY_CREATE $file2 ||
14954                 error "create $file2 failed"
14955         $OPENFILE -f O_CREAT:O_LOV_DELAY_CREATE $file3 ||
14956                 error "create $file3 failed"
14957         lovea1=$(get_layout_param $file1)
14958
14959         $LFS swap_layouts $file2 $file3 ||
14960                 error "swap $file2 $file3 layouts failed"
14961         $LFS swap_layouts $file1 $file2 ||
14962                 error "swap $file1 $file2 layouts failed"
14963
14964         lovea2=$(get_layout_param $file2)
14965         echo "$lovea1"
14966         echo "$lovea2"
14967         [ "$lovea1" == "$lovea2" ] || error "lovea $lovea1 != $lovea2"
14968
14969         lovea1=$(getfattr -n trusted.lov $file1 | grep ^trusted)
14970         [[ -z "$lovea1" ]] || error "$file1 shouldn't have lovea"
14971 }
14972 run_test 184d "allow stripeless layouts swap"
14973
14974 test_184e() {
14975         [[ $MDS1_VERSION -ge $(version_code 2.6.94) ]] ||
14976                 skip "Need MDS version at least 2.6.94"
14977         check_swap_layouts_support
14978         [ -z "$(which getfattr 2>/dev/null)" ] &&
14979                 skip_env "no getfattr command"
14980
14981         local file1=$DIR/$tdir/$tfile-1
14982         local file2=$DIR/$tdir/$tfile-2
14983         local file3=$DIR/$tdir/$tfile-3
14984         local lovea
14985
14986         mkdir -p $DIR/$tdir
14987         touch $file1 || error "create $file1 failed"
14988         $OPENFILE -f O_CREAT:O_LOV_DELAY_CREATE $file2 ||
14989                 error "create $file2 failed"
14990         $OPENFILE -f O_CREAT:O_LOV_DELAY_CREATE $file3 ||
14991                 error "create $file3 failed"
14992
14993         $LFS swap_layouts $file1 $file2 ||
14994                 error "swap $file1 $file2 layouts failed"
14995
14996         lovea=$(getfattr -n trusted.lov $file1 | grep ^trusted)
14997         [[ -z "$lovea" ]] || error "$file1 shouldn't have lovea"
14998
14999         echo 123 > $file1 || error "Should be able to write into $file1"
15000
15001         $LFS swap_layouts $file1 $file3 ||
15002                 error "swap $file1 $file3 layouts failed"
15003
15004         echo 123 > $file1 || error "Should be able to write into $file1"
15005
15006         rm -rf $file1 $file2 $file3
15007 }
15008 run_test 184e "Recreate layout after stripeless layout swaps"
15009
15010 test_184f() {
15011         # Create a file with name longer than sizeof(struct stat) ==
15012         # 144 to see if we can get chars from the file name to appear
15013         # in the returned striping. Note that 'f' == 0x66.
15014         local file=$(for ((i = 0; i < 200; i++)); do echo -n f; done)
15015
15016         mkdir -p $DIR/$tdir
15017         mcreate $DIR/$tdir/$file
15018         if lfs find --stripe-count 0x6666 $DIR/$tdir | grep $file; then
15019                 error "IOC_MDC_GETFILEINFO returned garbage striping"
15020         fi
15021 }
15022 run_test 184f "IOC_MDC_GETFILEINFO for files with long names but no striping"
15023
15024 test_185() { # LU-2441
15025         # LU-3553 - no volatile file support in old servers
15026         [[ $MDS1_VERSION -ge $(version_code 2.3.60) ]] ||
15027                 skip "Need MDS version at least 2.3.60"
15028
15029         mkdir -p $DIR/$tdir || error "creating dir $DIR/$tdir"
15030         touch $DIR/$tdir/spoo
15031         local mtime1=$(stat -c "%Y" $DIR/$tdir)
15032         local fid=$($MULTIOP $DIR/$tdir VFw4096c) ||
15033                 error "cannot create/write a volatile file"
15034         [ "$FILESET" == "" ] &&
15035         $CHECKSTAT -t file $MOUNT/.lustre/fid/$fid 2>/dev/null &&
15036                 error "FID is still valid after close"
15037
15038         multiop_bg_pause $DIR/$tdir vVw4096_c
15039         local multi_pid=$!
15040
15041         local OLD_IFS=$IFS
15042         IFS=":"
15043         local fidv=($fid)
15044         IFS=$OLD_IFS
15045         # assume that the next FID for this client is sequential, since stdout
15046         # is unfortunately eaten by multiop_bg_pause
15047         local n=$((${fidv[1]} + 1))
15048         local next_fid="${fidv[0]}:$(printf "0x%x" $n):${fidv[2]}"
15049         if [ "$FILESET" == "" ]; then
15050                 $CHECKSTAT -t file $MOUNT/.lustre/fid/$next_fid ||
15051                         error "FID is missing before close"
15052         fi
15053         kill -USR1 $multi_pid
15054         # 1 second delay, so if mtime change we will see it
15055         sleep 1
15056         local mtime2=$(stat -c "%Y" $DIR/$tdir)
15057         [[ $mtime1 == $mtime2 ]] || error "mtime has changed"
15058 }
15059 run_test 185 "Volatile file support"
15060
15061 function create_check_volatile() {
15062         local idx=$1
15063         local tgt
15064
15065         $MULTIOP $MOUNT/.lustre/fid V${idx}Fw4096_c >&/tmp/${tfile}.fid &
15066         local PID=$!
15067         sleep 1
15068         local FID=$(cat /tmp/${tfile}.fid)
15069         [ "$FID" == "" ] && error "can't get FID for volatile"
15070         $CHECKSTAT -t file $MOUNT/.lustre/fid/$FID || error "can't stat $FID"
15071         tgt=$($LFS getstripe -m $MOUNT/.lustre/fid/$FID)
15072         [ "$tgt" != "$idx" ] && error "wrong MDS $tgt, expected $idx"
15073         kill -USR1 $PID
15074         wait
15075         sleep 1
15076         cancel_lru_locks mdc # flush opencache
15077         $CHECKSTAT -t file $MOUNT/.lustre/fid/$FID && error "can stat $FID"
15078         return 0
15079 }
15080
15081 test_185a(){
15082         # LU-12516 - volatile creation via .lustre
15083         [[ $MDS1_VERSION -ge $(version_code 2.12.55) ]] ||
15084                 skip "Need MDS version at least 2.3.55"
15085
15086         create_check_volatile 0
15087         [ $MDSCOUNT -lt 2 ] && return 0
15088
15089         # DNE case
15090         create_check_volatile 1
15091
15092         return 0
15093 }
15094 run_test 185a "Volatile file creation in .lustre/fid/"
15095
15096 test_187a() {
15097         remote_mds_nodsh && skip "remote MDS with nodsh"
15098         [ $MDS1_VERSION -lt $(version_code 2.3.0) ] &&
15099                 skip "Need MDS version at least 2.3.0"
15100
15101         local dir0=$DIR/$tdir/$testnum
15102         mkdir -p $dir0 || error "creating dir $dir0"
15103
15104         local file=$dir0/file1
15105         dd if=/dev/urandom of=$file count=10 bs=1M conv=fsync
15106         local dv1=$($LFS data_version $file)
15107         dd if=/dev/urandom of=$file seek=10 count=1 bs=1M conv=fsync
15108         local dv2=$($LFS data_version $file)
15109         [[ $dv1 != $dv2 ]] ||
15110                 error "data version did not change on write $dv1 == $dv2"
15111
15112         # clean up
15113         rm -f $file1
15114 }
15115 run_test 187a "Test data version change"
15116
15117 test_187b() {
15118         remote_mds_nodsh && skip "remote MDS with nodsh"
15119         [ $MDS1_VERSION -lt $(version_code 2.3.0) ] &&
15120                 skip "Need MDS version at least 2.3.0"
15121
15122         local dir0=$DIR/$tdir/$testnum
15123         mkdir -p $dir0 || error "creating dir $dir0"
15124
15125         declare -a DV=$($MULTIOP $dir0 Vw1000xYw1000xY | cut -f3 -d" ")
15126         [[ ${DV[0]} != ${DV[1]} ]] ||
15127                 error "data version did not change on write"\
15128                       " ${DV[0]} == ${DV[1]}"
15129
15130         # clean up
15131         rm -f $file1
15132 }
15133 run_test 187b "Test data version change on volatile file"
15134
15135 test_200() {
15136         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15137         remote_mgs_nodsh && skip "remote MGS with nodsh"
15138         [ -n "$FILESET" ] && skip "SKIP due to FILESET set"
15139
15140         local POOL=${POOL:-cea1}
15141         local POOL_ROOT=${POOL_ROOT:-$DIR/d200.pools}
15142         local POOL_DIR_NAME=${POOL_DIR_NAME:-dir_tst}
15143         # Pool OST targets
15144         local first_ost=0
15145         local last_ost=$(($OSTCOUNT - 1))
15146         local ost_step=2
15147         local ost_list=$(seq $first_ost $ost_step $last_ost)
15148         local ost_range="$first_ost $last_ost $ost_step"
15149         local test_path=$POOL_ROOT/$POOL_DIR_NAME
15150         local file_dir=$POOL_ROOT/file_tst
15151         local subdir=$test_path/subdir
15152         local rc=0
15153
15154         while : ; do
15155                 # former test_200a test_200b
15156                 pool_add $POOL                          || { rc=$? ; break; }
15157                 pool_add_targets  $POOL $ost_range      || { rc=$? ; break; }
15158                 # former test_200c test_200d
15159                 mkdir -p $test_path
15160                 pool_set_dir      $POOL $test_path      || { rc=$? ; break; }
15161                 pool_check_dir    $POOL $test_path      || { rc=$? ; break; }
15162                 mkdir -p $subdir
15163                 pool_check_dir    $POOL $subdir         || { rc=$? ; break; }
15164                 pool_dir_rel_path $POOL $POOL_DIR_NAME $POOL_ROOT \
15165                                                         || { rc=$? ; break; }
15166                 # former test_200e test_200f
15167                 local files=$((OSTCOUNT*3))
15168                 pool_alloc_files  $POOL $test_path $files "$ost_list" \
15169                                                         || { rc=$? ; break; }
15170                 pool_create_files $POOL $file_dir $files "$ost_list" \
15171                                                         || { rc=$? ; break; }
15172                 # former test_200g test_200h
15173                 pool_lfs_df $POOL                       || { rc=$? ; break; }
15174                 pool_file_rel_path $POOL $test_path     || { rc=$? ; break; }
15175
15176                 # former test_201a test_201b test_201c
15177                 pool_remove_first_target $POOL          || { rc=$? ; break; }
15178
15179                 local f=$test_path/$tfile
15180                 pool_remove_all_targets $POOL $f        || { rc=$? ; break; }
15181                 pool_remove $POOL $f                    || { rc=$? ; break; }
15182                 break
15183         done
15184
15185         destroy_test_pools
15186
15187         return $rc
15188 }
15189 run_test 200 "OST pools"
15190
15191 # usage: default_attr <count | size | offset>
15192 default_attr() {
15193         $LCTL get_param -n lov.$FSNAME-clilov-\*.stripe${1}
15194 }
15195
15196 # usage: check_default_stripe_attr
15197 check_default_stripe_attr() {
15198         ACTUAL=$($LFS getstripe $* $DIR/$tdir)
15199         case $1 in
15200         --stripe-count|-c)
15201                 [ -n "$2" ] && EXPECTED=0 || EXPECTED=$(default_attr count);;
15202         --stripe-size|-S)
15203                 [ -n "$2" ] && EXPECTED=0 || EXPECTED=$(default_attr size);;
15204         --stripe-index|-i)
15205                 EXPECTED=-1;;
15206         *)
15207                 error "unknown getstripe attr '$1'"
15208         esac
15209
15210         [ $ACTUAL == $EXPECTED ] ||
15211                 error "$DIR/$tdir has $1 '$ACTUAL', not '$EXPECTED'"
15212 }
15213
15214 test_204a() {
15215         test_mkdir $DIR/$tdir
15216         $LFS setstripe --stripe-count 0 --stripe-size 0 --stripe-index -1 $DIR/$tdir
15217
15218         check_default_stripe_attr --stripe-count
15219         check_default_stripe_attr --stripe-size
15220         check_default_stripe_attr --stripe-index
15221 }
15222 run_test 204a "Print default stripe attributes"
15223
15224 test_204b() {
15225         test_mkdir $DIR/$tdir
15226         $LFS setstripe --stripe-count 1 $DIR/$tdir
15227
15228         check_default_stripe_attr --stripe-size
15229         check_default_stripe_attr --stripe-index
15230 }
15231 run_test 204b "Print default stripe size and offset"
15232
15233 test_204c() {
15234         test_mkdir $DIR/$tdir
15235         $LFS setstripe --stripe-size 65536 $DIR/$tdir
15236
15237         check_default_stripe_attr --stripe-count
15238         check_default_stripe_attr --stripe-index
15239 }
15240 run_test 204c "Print default stripe count and offset"
15241
15242 test_204d() {
15243         test_mkdir $DIR/$tdir
15244         $LFS setstripe --stripe-index 0 $DIR/$tdir
15245
15246         check_default_stripe_attr --stripe-count
15247         check_default_stripe_attr --stripe-size
15248 }
15249 run_test 204d "Print default stripe count and size"
15250
15251 test_204e() {
15252         test_mkdir $DIR/$tdir
15253         $LFS setstripe -d $DIR/$tdir
15254
15255         check_default_stripe_attr --stripe-count --raw
15256         check_default_stripe_attr --stripe-size --raw
15257         check_default_stripe_attr --stripe-index --raw
15258 }
15259 run_test 204e "Print raw stripe attributes"
15260
15261 test_204f() {
15262         test_mkdir $DIR/$tdir
15263         $LFS setstripe --stripe-count 1 $DIR/$tdir
15264
15265         check_default_stripe_attr --stripe-size --raw
15266         check_default_stripe_attr --stripe-index --raw
15267 }
15268 run_test 204f "Print raw stripe size and offset"
15269
15270 test_204g() {
15271         test_mkdir $DIR/$tdir
15272         $LFS setstripe --stripe-size 65536 $DIR/$tdir
15273
15274         check_default_stripe_attr --stripe-count --raw
15275         check_default_stripe_attr --stripe-index --raw
15276 }
15277 run_test 204g "Print raw stripe count and offset"
15278
15279 test_204h() {
15280         test_mkdir $DIR/$tdir
15281         $LFS setstripe --stripe-index 0 $DIR/$tdir
15282
15283         check_default_stripe_attr --stripe-count --raw
15284         check_default_stripe_attr --stripe-size --raw
15285 }
15286 run_test 204h "Print raw stripe count and size"
15287
15288 # Figure out which job scheduler is being used, if any,
15289 # or use a fake one
15290 if [ -n "$SLURM_JOB_ID" ]; then # SLURM
15291         JOBENV=SLURM_JOB_ID
15292 elif [ -n "$LSB_JOBID" ]; then # Load Sharing Facility
15293         JOBENV=LSB_JOBID
15294 elif [ -n "$PBS_JOBID" ]; then # PBS/Maui/Moab
15295         JOBENV=PBS_JOBID
15296 elif [ -n "$LOADL_STEPID" ]; then # LoadLeveller
15297         JOBENV=LOADL_STEP_ID
15298 elif [ -n "$JOB_ID" ]; then # Sun Grid Engine
15299         JOBENV=JOB_ID
15300 else
15301         $LCTL list_param jobid_name > /dev/null 2>&1
15302         if [ $? -eq 0 ]; then
15303                 JOBENV=nodelocal
15304         else
15305                 JOBENV=FAKE_JOBID
15306         fi
15307 fi
15308 LUSTRE_JOBID_SIZE=31 # plus NUL terminator
15309
15310 verify_jobstats() {
15311         local cmd=($1)
15312         shift
15313         local facets="$@"
15314
15315 # we don't really need to clear the stats for this test to work, since each
15316 # command has a unique jobid, but it makes debugging easier if needed.
15317 #       for facet in $facets; do
15318 #               local dev=$(convert_facet2label $facet)
15319 #               # clear old jobstats
15320 #               do_facet $facet lctl set_param *.$dev.job_stats="clear"
15321 #       done
15322
15323         # use a new JobID for each test, or we might see an old one
15324         [ "$JOBENV" = "FAKE_JOBID" ] &&
15325                 FAKE_JOBID=id.$testnum.$(basename ${cmd[0]}).$RANDOM
15326
15327         JOBVAL=${!JOBENV:0:$LUSTRE_JOBID_SIZE}
15328
15329         [ "$JOBENV" = "nodelocal" ] && {
15330                 FAKE_JOBID=id.$testnum.%e.$RANDOM
15331                 $LCTL set_param jobid_name=$FAKE_JOBID
15332                 JOBVAL=${FAKE_JOBID/\%e/$(basename ${cmd[0]})}
15333         }
15334
15335         log "Test: ${cmd[*]}"
15336         log "Using JobID environment $($LCTL get_param -n jobid_var)=$JOBVAL"
15337
15338         if [ $JOBENV = "FAKE_JOBID" ]; then
15339                 FAKE_JOBID=$JOBVAL ${cmd[*]}
15340         else
15341                 ${cmd[*]}
15342         fi
15343
15344         # all files are created on OST0000
15345         for facet in $facets; do
15346                 local stats="*.$(convert_facet2label $facet).job_stats"
15347
15348                 # strip out libtool wrappers for in-tree executables
15349                 if [ $(do_facet $facet lctl get_param $stats |
15350                        sed -e 's/\.lt-/./' | grep -c $JOBVAL) -ne 1 ]; then
15351                         do_facet $facet lctl get_param $stats
15352                         error "No jobstats for $JOBVAL found on $facet::$stats"
15353                 fi
15354         done
15355 }
15356
15357 jobstats_set() {
15358         local new_jobenv=$1
15359
15360         set_persistent_param_and_check client "jobid_var" \
15361                 "$FSNAME.sys.jobid_var" $new_jobenv
15362 }
15363
15364 test_205() { # Job stats
15365         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15366         [[ $MDS1_VERSION -ge $(version_code 2.7.1) ]] ||
15367                 skip "Need MDS version with at least 2.7.1"
15368         remote_mgs_nodsh && skip "remote MGS with nodsh"
15369         remote_mds_nodsh && skip "remote MDS with nodsh"
15370         remote_ost_nodsh && skip "remote OST with nodsh"
15371         [ -z "$(lctl get_param -n mdc.*.connect_flags | grep jobstats)" ] &&
15372                 skip "Server doesn't support jobstats"
15373         [[ $JOBID_VAR = disable ]] && skip_env "jobstats is disabled"
15374
15375         local old_jobenv=$($LCTL get_param -n jobid_var)
15376         [ $old_jobenv != $JOBENV ] && jobstats_set $JOBENV
15377
15378         if [[ $PERM_CMD == *"set_param -P"* ]]; then
15379                 stack_trap "do_facet mgs $PERM_CMD jobid_var=$old_jobenv" EXIT
15380         else
15381                 stack_trap "do_facet mgs $PERM_CMD \
15382                         $FSNAME.sys.jobid_var=$old_jobenv" EXIT
15383         fi
15384         changelog_register
15385
15386         local old_interval=$(do_facet $SINGLEMDS lctl get_param -n \
15387                                 mdt.*.job_cleanup_interval | head -n 1)
15388         local new_interval=5
15389         do_facet $SINGLEMDS \
15390                 $LCTL set_param mdt.*.job_cleanup_interval=$new_interval
15391         stack_trap "do_facet $SINGLEMDS \
15392                 $LCTL set_param mdt.*.job_cleanup_interval=$old_interval" EXIT
15393         local start=$SECONDS
15394
15395         local cmd
15396         # mkdir
15397         cmd="mkdir $DIR/$tdir"
15398         verify_jobstats "$cmd" "$SINGLEMDS"
15399         # rmdir
15400         cmd="rmdir $DIR/$tdir"
15401         verify_jobstats "$cmd" "$SINGLEMDS"
15402         # mkdir on secondary MDT
15403         if [ $MDSCOUNT -gt 1 ]; then
15404                 cmd="lfs mkdir -i 1 $DIR/$tdir.remote"
15405                 verify_jobstats "$cmd" "mds2"
15406         fi
15407         # mknod
15408         cmd="mknod $DIR/$tfile c 1 3"
15409         verify_jobstats "$cmd" "$SINGLEMDS"
15410         # unlink
15411         cmd="rm -f $DIR/$tfile"
15412         verify_jobstats "$cmd" "$SINGLEMDS"
15413         # create all files on OST0000 so verify_jobstats can find OST stats
15414         # open & close
15415         cmd="$LFS setstripe -i 0 -c 1 $DIR/$tfile"
15416         verify_jobstats "$cmd" "$SINGLEMDS"
15417         # setattr
15418         cmd="touch $DIR/$tfile"
15419         verify_jobstats "$cmd" "$SINGLEMDS ost1"
15420         # write
15421         cmd="dd if=/dev/zero of=$DIR/$tfile bs=1M count=1 oflag=sync"
15422         verify_jobstats "$cmd" "ost1"
15423         # read
15424         cancel_lru_locks osc
15425         cmd="dd if=$DIR/$tfile of=/dev/null bs=1M count=1 iflag=direct"
15426         verify_jobstats "$cmd" "ost1"
15427         # truncate
15428         cmd="$TRUNCATE $DIR/$tfile 0"
15429         verify_jobstats "$cmd" "$SINGLEMDS ost1"
15430         # rename
15431         cmd="mv -f $DIR/$tfile $DIR/$tdir.rename"
15432         verify_jobstats "$cmd" "$SINGLEMDS"
15433         # jobstats expiry - sleep until old stats should be expired
15434         local left=$((new_interval + 5 - (SECONDS - start)))
15435         [ $left -ge 0 ] && wait_update_facet $SINGLEMDS \
15436                 "lctl get_param *.*.job_stats | grep -c 'job_id.*mkdir'" \
15437                         "0" $left
15438         cmd="mkdir $DIR/$tdir.expire"
15439         verify_jobstats "$cmd" "$SINGLEMDS"
15440         [ $(do_facet $SINGLEMDS lctl get_param *.*.job_stats |
15441             grep -c "job_id.*mkdir") -gt 1 ] && error "old jobstats not expired"
15442
15443         # Ensure that jobid are present in changelog (if supported by MDS)
15444         if [ $MDS1_VERSION -ge $(version_code 2.6.52) ];then
15445                 changelog_dump | tail -10
15446                 jobids=$(changelog_dump | tail -9 | grep -c "j=")
15447                 [ $jobids -eq 9 ] ||
15448                         error "Wrong changelog jobid count $jobids != 9"
15449
15450                 # LU-5862
15451                 JOBENV="disable"
15452                 jobstats_set $JOBENV
15453                 touch $DIR/$tfile
15454                 changelog_dump | grep $tfile
15455                 jobids=$(changelog_dump | grep $tfile | tail -1 | grep -c "j=")
15456                 [ $jobids -eq 0 ] ||
15457                         error "Unexpected jobids when jobid_var=$JOBENV"
15458         fi
15459
15460         lctl set_param jobid_var=USER jobid_name="S.%j.%e.%u.%h.E"
15461         JOBENV="JOBCOMPLEX"
15462         JOBCOMPLEX="S.$USER.touch.$(id -u).$(hostname).E"
15463
15464         verify_jobstats "touch $DIR/$tfile" $SINGLEMDS
15465 }
15466 run_test 205 "Verify job stats"
15467
15468 # LU-1480, LU-1773 and LU-1657
15469 test_206() {
15470         mkdir -p $DIR/$tdir
15471         $LFS setstripe -c -1 $DIR/$tdir
15472 #define OBD_FAIL_LOV_INIT 0x1403
15473         $LCTL set_param fail_loc=0xa0001403
15474         $LCTL set_param fail_val=1
15475         touch $DIR/$tdir/$tfile || true
15476 }
15477 run_test 206 "fail lov_init_raid0() doesn't lbug"
15478
15479 test_207a() {
15480         dd if=/dev/zero of=$DIR/$tfile bs=4k count=$((RANDOM%10+1))
15481         local fsz=`stat -c %s $DIR/$tfile`
15482         cancel_lru_locks mdc
15483
15484         # do not return layout in getattr intent
15485 #define OBD_FAIL_MDS_NO_LL_GETATTR 0x170
15486         $LCTL set_param fail_loc=0x170
15487         local sz=`stat -c %s $DIR/$tfile`
15488
15489         [ $fsz -eq $sz ] || error "file size expected $fsz, actual $sz"
15490
15491         rm -rf $DIR/$tfile
15492 }
15493 run_test 207a "can refresh layout at glimpse"
15494
15495 test_207b() {
15496         dd if=/dev/zero of=$DIR/$tfile bs=4k count=$((RANDOM%10+1))
15497         local cksum=`md5sum $DIR/$tfile`
15498         local fsz=`stat -c %s $DIR/$tfile`
15499         cancel_lru_locks mdc
15500         cancel_lru_locks osc
15501
15502         # do not return layout in getattr intent
15503 #define OBD_FAIL_MDS_NO_LL_OPEN 0x171
15504         $LCTL set_param fail_loc=0x171
15505
15506         # it will refresh layout after the file is opened but before read issues
15507         echo checksum is "$cksum"
15508         echo "$cksum" |md5sum -c --quiet || error "file differs"
15509
15510         rm -rf $DIR/$tfile
15511 }
15512 run_test 207b "can refresh layout at open"
15513
15514 test_208() {
15515         # FIXME: in this test suite, only RD lease is used. This is okay
15516         # for now as only exclusive open is supported. After generic lease
15517         # is done, this test suite should be revised. - Jinshan
15518
15519         remote_mds_nodsh && skip "remote MDS with nodsh"
15520         [[ $MDS1_VERSION -ge $(version_code 2.4.52) ]] ||
15521                 skip "Need MDS version at least 2.4.52"
15522
15523         echo "==== test 1: verify get lease work"
15524         $MULTIOP $DIR/$tfile oO_CREAT:O_RDWR:eRE+eU || error "get lease error"
15525
15526         echo "==== test 2: verify lease can be broken by upcoming open"
15527         $MULTIOP $DIR/$tfile oO_RDONLY:eR_E-eUc &
15528         local PID=$!
15529         sleep 1
15530
15531         $MULTIOP $DIR/$tfile oO_RDONLY:c
15532         kill -USR1 $PID && wait $PID || error "break lease error"
15533
15534         echo "==== test 3: verify lease can't be granted if an open already exists"
15535         $MULTIOP $DIR/$tfile oO_RDONLY:_c &
15536         local PID=$!
15537         sleep 1
15538
15539         $MULTIOP $DIR/$tfile oO_RDONLY:eReUc && error "apply lease should fail"
15540         kill -USR1 $PID && wait $PID || error "open file error"
15541
15542         echo "==== test 4: lease can sustain over recovery"
15543         $MULTIOP $DIR/$tfile oO_RDONLY:eR_E+eUc &
15544         PID=$!
15545         sleep 1
15546
15547         fail mds1
15548
15549         kill -USR1 $PID && wait $PID || error "lease broken over recovery"
15550
15551         echo "==== test 5: lease broken can't be regained by replay"
15552         $MULTIOP $DIR/$tfile oO_RDONLY:eR_E-eUc &
15553         PID=$!
15554         sleep 1
15555
15556         # open file to break lease and then recovery
15557         $MULTIOP $DIR/$tfile oO_RDWR:c || error "open file error"
15558         fail mds1
15559
15560         kill -USR1 $PID && wait $PID || error "lease not broken over recovery"
15561
15562         rm -f $DIR/$tfile
15563 }
15564 run_test 208 "Exclusive open"
15565
15566 test_209() {
15567         [ -z "$(lctl get_param -n mdc.*.connect_flags | grep disp_stripe)" ] &&
15568                 skip_env "must have disp_stripe"
15569
15570         touch $DIR/$tfile
15571         sync; sleep 5; sync;
15572
15573         echo 3 > /proc/sys/vm/drop_caches
15574         req_before=$(awk '/ptlrpc_cache / { print $2 }' /proc/slabinfo)
15575
15576         # open/close 500 times
15577         for i in $(seq 500); do
15578                 cat $DIR/$tfile
15579         done
15580
15581         echo 3 > /proc/sys/vm/drop_caches
15582         req_after=$(awk '/ptlrpc_cache / { print $2 }' /proc/slabinfo)
15583
15584         echo "before: $req_before, after: $req_after"
15585         [ $((req_after - req_before)) -ge 300 ] &&
15586                 error "open/close requests are not freed"
15587         return 0
15588 }
15589 run_test 209 "read-only open/close requests should be freed promptly"
15590
15591 test_212() {
15592         size=`date +%s`
15593         size=$((size % 8192 + 1))
15594         dd if=/dev/urandom of=$DIR/f212 bs=1k count=$size
15595         sendfile $DIR/f212 $DIR/f212.xyz || error "sendfile wrong"
15596         rm -f $DIR/f212 $DIR/f212.xyz
15597 }
15598 run_test 212 "Sendfile test ============================================"
15599
15600 test_213() {
15601         dd if=/dev/zero of=$DIR/$tfile bs=4k count=4
15602         cancel_lru_locks osc
15603         lctl set_param fail_loc=0x8000040f
15604         # generate a read lock
15605         cat $DIR/$tfile > /dev/null
15606         # write to the file, it will try to cancel the above read lock.
15607         cat /etc/hosts >> $DIR/$tfile
15608 }
15609 run_test 213 "OSC lock completion and cancel race don't crash - bug 18829"
15610
15611 test_214() { # for bug 20133
15612         mkdir -p $DIR/$tdir/d214c || error "mkdir $DIR/$tdir/d214c failed"
15613         for (( i=0; i < 340; i++ )) ; do
15614                 touch $DIR/$tdir/d214c/a$i
15615         done
15616
15617         ls -l $DIR/$tdir || error "ls -l $DIR/d214p failed"
15618         mv $DIR/$tdir/d214c $DIR/ || error "mv $DIR/d214p/d214c $DIR/ failed"
15619         ls $DIR/d214c || error "ls $DIR/d214c failed"
15620         rm -rf $DIR/$tdir || error "rm -rf $DIR/d214* failed"
15621         rm -rf $DIR/d214* || error "rm -rf $DIR/d214* failed"
15622 }
15623 run_test 214 "hash-indexed directory test - bug 20133"
15624
15625 # having "abc" as 1st arg, creates $TMP/lnet_abc.out and $TMP/lnet_abc.sys
15626 create_lnet_proc_files() {
15627         lctl get_param -n $1 >$TMP/lnet_$1.sys || error "cannot read lnet.$1"
15628 }
15629
15630 # counterpart of create_lnet_proc_files
15631 remove_lnet_proc_files() {
15632         rm -f $TMP/lnet_$1.sys
15633 }
15634
15635 # uses 1st arg as trailing part of filename, 2nd arg as description for reports,
15636 # 3rd arg as regexp for body
15637 check_lnet_proc_stats() {
15638         local l=$(cat "$TMP/lnet_$1" |wc -l)
15639         [ $l = 1 ] || (cat "$TMP/lnet_$1" && error "$2 is not of 1 line: $l")
15640
15641         grep -E "$3" "$TMP/lnet_$1" || (cat "$TMP/lnet_$1" && error "$2 misformatted")
15642 }
15643
15644 # uses 1st arg as trailing part of filename, 2nd arg as description for reports,
15645 # 3rd arg as regexp for body, 4th arg as regexp for 1st line, 5th arg is
15646 # optional and can be regexp for 2nd line (lnet.routes case)
15647 check_lnet_proc_entry() {
15648         local blp=2          # blp stands for 'position of 1st line of body'
15649         [ -z "$5" ] || blp=3 # lnet.routes case
15650
15651         local l=$(cat "$TMP/lnet_$1" |wc -l)
15652         # subtracting one from $blp because the body can be empty
15653         [ "$l" -ge "$(($blp - 1))" ] || (cat "$TMP/lnet_$1" && error "$2 is too short: $l")
15654
15655         sed -n '1 p' "$TMP/lnet_$1" |grep -E "$4" >/dev/null ||
15656                 (cat "$TMP/lnet_$1" && error "1st line of $2 misformatted")
15657
15658         [ "$5" = "" ] || sed -n '2 p' "$TMP/lnet_$1" |grep -E "$5" >/dev/null ||
15659                 (cat "$TMP/lnet_$1" && error "2nd line of $2 misformatted")
15660
15661         # bail out if any unexpected line happened
15662         sed -n "$blp p" "$TMP/lnet_$1" | grep -Ev "$3"
15663         [ "$?" != 0 ] || error "$2 misformatted"
15664 }
15665
15666 test_215() { # for bugs 18102, 21079, 21517
15667         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15668
15669         local N='(0|[1-9][0-9]*)'       # non-negative numeric
15670         local P='[1-9][0-9]*'           # positive numeric
15671         local I='(0|-?[1-9][0-9]*|NA)'  # any numeric (0 | >0 | <0) or NA if no value
15672         local NET='[a-z][a-z0-9]*'      # LNET net like o2ib2
15673         local ADDR='[0-9.]+'            # LNET addr like 10.0.0.1
15674         local NID="$ADDR@$NET"          # LNET nid like 10.0.0.1@o2ib2
15675
15676         local L1 # regexp for 1st line
15677         local L2 # regexp for 2nd line (optional)
15678         local BR # regexp for the rest (body)
15679
15680         # lnet.stats should look as 11 space-separated non-negative numerics
15681         BR="^$N $N $N $N $N $N $N $N $N $N $N$"
15682         create_lnet_proc_files "stats"
15683         check_lnet_proc_stats "stats.sys" "lnet.stats" "$BR"
15684         remove_lnet_proc_files "stats"
15685
15686         # lnet.routes should look like this:
15687         # Routing disabled/enabled
15688         # net hops priority state router
15689         # where net is a string like tcp0, hops > 0, priority >= 0,
15690         # state is up/down,
15691         # router is a string like 192.168.1.1@tcp2
15692         L1="^Routing (disabled|enabled)$"
15693         L2="^net +hops +priority +state +router$"
15694         BR="^$NET +$N +(0|1) +(up|down) +$NID$"
15695         create_lnet_proc_files "routes"
15696         check_lnet_proc_entry "routes.sys" "lnet.routes" "$BR" "$L1" "$L2"
15697         remove_lnet_proc_files "routes"
15698
15699         # lnet.routers should look like this:
15700         # ref rtr_ref alive_cnt state last_ping ping_sent deadline down_ni router
15701         # where ref > 0, rtr_ref > 0, alive_cnt >= 0, state is up/down,
15702         # last_ping >= 0, ping_sent is boolean (0/1), deadline and down_ni are
15703         # numeric (0 or >0 or <0), router is a string like 192.168.1.1@tcp2
15704         L1="^ref +rtr_ref +alive +router$"
15705         BR="^$P +$P +(up|down) +$NID$"
15706         create_lnet_proc_files "routers"
15707         check_lnet_proc_entry "routers.sys" "lnet.routers" "$BR" "$L1"
15708         remove_lnet_proc_files "routers"
15709
15710         # lnet.peers should look like this:
15711         # nid refs state last max rtr min tx min queue
15712         # where nid is a string like 192.168.1.1@tcp2, refs > 0,
15713         # state is up/down/NA, max >= 0. last, rtr, min, tx, min are
15714         # numeric (0 or >0 or <0), queue >= 0.
15715         L1="^nid +refs +state +last +max +rtr +min +tx +min +queue$"
15716         BR="^$NID +$P +(up|down|NA) +$I +$N +$I +$I +$I +$I +$N$"
15717         create_lnet_proc_files "peers"
15718         check_lnet_proc_entry "peers.sys" "lnet.peers" "$BR" "$L1"
15719         remove_lnet_proc_files "peers"
15720
15721         # lnet.buffers  should look like this:
15722         # pages count credits min
15723         # where pages >=0, count >=0, credits and min are numeric (0 or >0 or <0)
15724         L1="^pages +count +credits +min$"
15725         BR="^ +$N +$N +$I +$I$"
15726         create_lnet_proc_files "buffers"
15727         check_lnet_proc_entry "buffers.sys" "lnet.buffers" "$BR" "$L1"
15728         remove_lnet_proc_files "buffers"
15729
15730         # lnet.nis should look like this:
15731         # nid status alive refs peer rtr max tx min
15732         # where nid is a string like 192.168.1.1@tcp2, status is up/down,
15733         # alive is numeric (0 or >0 or <0), refs >= 0, peer >= 0,
15734         # rtr >= 0, max >=0, tx and min are numeric (0 or >0 or <0).
15735         L1="^nid +status +alive +refs +peer +rtr +max +tx +min$"
15736         BR="^$NID +(up|down) +$I +$N +$N +$N +$N +$I +$I$"
15737         create_lnet_proc_files "nis"
15738         check_lnet_proc_entry "nis.sys" "lnet.nis" "$BR" "$L1"
15739         remove_lnet_proc_files "nis"
15740
15741         # can we successfully write to lnet.stats?
15742         lctl set_param -n stats=0 || error "cannot write to lnet.stats"
15743 }
15744 run_test 215 "lnet exists and has proper content - bugs 18102, 21079, 21517"
15745
15746 test_216() { # bug 20317
15747         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15748         remote_ost_nodsh && skip "remote OST with nodsh"
15749
15750         local node
15751         local facets=$(get_facets OST)
15752         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
15753
15754         save_lustre_params client "osc.*.contention_seconds" > $p
15755         save_lustre_params $facets \
15756                 "ldlm.namespaces.filter-*.max_nolock_bytes" >> $p
15757         save_lustre_params $facets \
15758                 "ldlm.namespaces.filter-*.contended_locks" >> $p
15759         save_lustre_params $facets \
15760                 "ldlm.namespaces.filter-*.contention_seconds" >> $p
15761         clear_stats osc.*.osc_stats
15762
15763         # agressive lockless i/o settings
15764         do_nodes $(comma_list $(osts_nodes)) \
15765                 "lctl set_param -n ldlm.namespaces.*.max_nolock_bytes=2000000 \
15766                         ldlm.namespaces.filter-*.contended_locks=0 \
15767                         ldlm.namespaces.filter-*.contention_seconds=60"
15768         lctl set_param -n osc.*.contention_seconds=60
15769
15770         $DIRECTIO write $DIR/$tfile 0 10 4096
15771         $CHECKSTAT -s 40960 $DIR/$tfile
15772
15773         # disable lockless i/o
15774         do_nodes $(comma_list $(osts_nodes)) \
15775                 "lctl set_param -n ldlm.namespaces.filter-*.max_nolock_bytes=0 \
15776                         ldlm.namespaces.filter-*.contended_locks=32 \
15777                         ldlm.namespaces.filter-*.contention_seconds=0"
15778         lctl set_param -n osc.*.contention_seconds=0
15779         clear_stats osc.*.osc_stats
15780
15781         dd if=/dev/zero of=$DIR/$tfile count=0
15782         $CHECKSTAT -s 0 $DIR/$tfile
15783
15784         restore_lustre_params <$p
15785         rm -f $p
15786         rm $DIR/$tfile
15787 }
15788 run_test 216 "check lockless direct write updates file size and kms correctly"
15789
15790 test_217() { # bug 22430
15791         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15792
15793         local node
15794         local nid
15795
15796         for node in $(nodes_list); do
15797                 nid=$(host_nids_address $node $NETTYPE)
15798                 if [[ $nid = *-* ]] ; then
15799                         echo "lctl ping $(h2nettype $nid)"
15800                         lctl ping $(h2nettype $nid)
15801                 else
15802                         echo "skipping $node (no hyphen detected)"
15803                 fi
15804         done
15805 }
15806 run_test 217 "check lctl ping for hostnames with hiphen ('-')"
15807
15808 test_218() {
15809        # do directio so as not to populate the page cache
15810        log "creating a 10 Mb file"
15811        $MULTIOP $DIR/$tfile oO_CREAT:O_DIRECT:O_RDWR:w$((10*1048576))c || error "multiop failed while creating a file"
15812        log "starting reads"
15813        dd if=$DIR/$tfile of=/dev/null bs=4096 &
15814        log "truncating the file"
15815        $MULTIOP $DIR/$tfile oO_TRUNC:c || error "multiop failed while truncating the file"
15816        log "killing dd"
15817        kill %+ || true # reads might have finished
15818        echo "wait until dd is finished"
15819        wait
15820        log "removing the temporary file"
15821        rm -rf $DIR/$tfile || error "tmp file removal failed"
15822 }
15823 run_test 218 "parallel read and truncate should not deadlock"
15824
15825 test_219() {
15826         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15827
15828         # write one partial page
15829         dd if=/dev/zero of=$DIR/$tfile bs=1024 count=1
15830         # set no grant so vvp_io_commit_write will do sync write
15831         $LCTL set_param fail_loc=0x411
15832         # write a full page at the end of file
15833         dd if=/dev/zero of=$DIR/$tfile bs=4096 count=1 seek=1 conv=notrunc
15834
15835         $LCTL set_param fail_loc=0
15836         dd if=/dev/zero of=$DIR/$tfile bs=4096 count=1 seek=3
15837         $LCTL set_param fail_loc=0x411
15838         dd if=/dev/zero of=$DIR/$tfile bs=1024 count=1 seek=2 conv=notrunc
15839
15840         # LU-4201
15841         dd if=/dev/zero of=$DIR/$tfile-2 bs=1024 count=1
15842         $CHECKSTAT -s 1024 $DIR/$tfile-2 || error "checkstat wrong size"
15843 }
15844 run_test 219 "LU-394: Write partial won't cause uncontiguous pages vec at LND"
15845
15846 test_220() { #LU-325
15847         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15848         remote_ost_nodsh && skip "remote OST with nodsh"
15849         remote_mds_nodsh && skip "remote MDS with nodsh"
15850         remote_mgs_nodsh && skip "remote MGS with nodsh"
15851
15852         local OSTIDX=0
15853
15854         # create on MDT0000 so the last_id and next_id are correct
15855         mkdir $DIR/$tdir
15856         local OST=$($LFS df $DIR | awk '/OST:'$OSTIDX'/ { print $1 }')
15857         OST=${OST%_UUID}
15858
15859         # on the mdt's osc
15860         local mdtosc_proc1=$(get_mdtosc_proc_path $SINGLEMDS $OST)
15861         local last_id=$(do_facet $SINGLEMDS lctl get_param -n \
15862                         osp.$mdtosc_proc1.prealloc_last_id)
15863         local next_id=$(do_facet $SINGLEMDS lctl get_param -n \
15864                         osp.$mdtosc_proc1.prealloc_next_id)
15865
15866         $LFS df -i
15867
15868         do_facet ost$((OSTIDX + 1)) lctl set_param fail_val=-1
15869         #define OBD_FAIL_OST_ENOINO              0x229
15870         do_facet ost$((OSTIDX + 1)) lctl set_param fail_loc=0x229
15871         create_pool $FSNAME.$TESTNAME || return 1
15872         do_facet mgs $LCTL pool_add $FSNAME.$TESTNAME $OST || return 2
15873
15874         $LFS setstripe $DIR/$tdir -i $OSTIDX -c 1 -p $FSNAME.$TESTNAME
15875
15876         MDSOBJS=$((last_id - next_id))
15877         echo "preallocated objects on MDS is $MDSOBJS" "($last_id - $next_id)"
15878
15879         blocks=$($LFS df $MOUNT | awk '($1 == '$OSTIDX') { print $4 }')
15880         echo "OST still has $count kbytes free"
15881
15882         echo "create $MDSOBJS files @next_id..."
15883         createmany -o $DIR/$tdir/f $MDSOBJS || return 3
15884
15885         local last_id2=$(do_facet mds${MDSIDX} lctl get_param -n \
15886                         osp.$mdtosc_proc1.prealloc_last_id)
15887         local next_id2=$(do_facet mds${MDSIDX} lctl get_param -n \
15888                         osp.$mdtosc_proc1.prealloc_next_id)
15889
15890         echo "after creation, last_id=$last_id2, next_id=$next_id2"
15891         $LFS df -i
15892
15893         echo "cleanup..."
15894
15895         do_facet ost$((OSTIDX + 1)) lctl set_param fail_val=0
15896         do_facet ost$((OSTIDX + 1)) lctl set_param fail_loc=0
15897
15898         do_facet mgs $LCTL pool_remove $FSNAME.$TESTNAME $OST ||
15899                 error "$LCTL pool_remove $FSNAME.$TESTNAME $OST failed"
15900         do_facet mgs $LCTL pool_destroy $FSNAME.$TESTNAME ||
15901                 error "$LCTL pool_destroy $FSNAME.$TESTNAME failed"
15902         echo "unlink $MDSOBJS files @$next_id..."
15903         unlinkmany $DIR/$tdir/f $MDSOBJS || error "unlinkmany failed"
15904 }
15905 run_test 220 "preallocated MDS objects still used if ENOSPC from OST"
15906
15907 test_221() {
15908         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15909
15910         dd if=`which date` of=$MOUNT/date oflag=sync
15911         chmod +x $MOUNT/date
15912
15913         #define OBD_FAIL_LLITE_FAULT_TRUNC_RACE  0x1401
15914         $LCTL set_param fail_loc=0x80001401
15915
15916         $MOUNT/date > /dev/null
15917         rm -f $MOUNT/date
15918 }
15919 run_test 221 "make sure fault and truncate race to not cause OOM"
15920
15921 test_222a () {
15922         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15923
15924         rm -rf $DIR/$tdir
15925         test_mkdir $DIR/$tdir
15926         $LFS setstripe -c 1 -i 0 $DIR/$tdir
15927         createmany -o $DIR/$tdir/$tfile 10
15928         cancel_lru_locks mdc
15929         cancel_lru_locks osc
15930         #define OBD_FAIL_LDLM_AGL_DELAY           0x31a
15931         $LCTL set_param fail_loc=0x31a
15932         ls -l $DIR/$tdir > /dev/null || error "AGL for ls failed"
15933         $LCTL set_param fail_loc=0
15934         rm -r $DIR/$tdir
15935 }
15936 run_test 222a "AGL for ls should not trigger CLIO lock failure"
15937
15938 test_222b () {
15939         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15940
15941         rm -rf $DIR/$tdir
15942         test_mkdir $DIR/$tdir
15943         $LFS setstripe -c 1 -i 0 $DIR/$tdir
15944         createmany -o $DIR/$tdir/$tfile 10
15945         cancel_lru_locks mdc
15946         cancel_lru_locks osc
15947         #define OBD_FAIL_LDLM_AGL_DELAY           0x31a
15948         $LCTL set_param fail_loc=0x31a
15949         rm -r $DIR/$tdir || error "AGL for rmdir failed"
15950         $LCTL set_param fail_loc=0
15951 }
15952 run_test 222b "AGL for rmdir should not trigger CLIO lock failure"
15953
15954 test_223 () {
15955         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15956
15957         rm -rf $DIR/$tdir
15958         test_mkdir $DIR/$tdir
15959         $LFS setstripe -c 1 -i 0 $DIR/$tdir
15960         createmany -o $DIR/$tdir/$tfile 10
15961         cancel_lru_locks mdc
15962         cancel_lru_locks osc
15963         #define OBD_FAIL_LDLM_AGL_NOLOCK          0x31b
15964         $LCTL set_param fail_loc=0x31b
15965         ls -l $DIR/$tdir > /dev/null || error "reenqueue failed"
15966         $LCTL set_param fail_loc=0
15967         rm -r $DIR/$tdir
15968 }
15969 run_test 223 "osc reenqueue if without AGL lock granted ======================="
15970
15971 test_224a() { # LU-1039, MRP-303
15972         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15973
15974         #define OBD_FAIL_PTLRPC_CLIENT_BULK_CB   0x508
15975         $LCTL set_param fail_loc=0x508
15976         dd if=/dev/zero of=$DIR/$tfile bs=4096 count=1 conv=fsync
15977         $LCTL set_param fail_loc=0
15978         df $DIR
15979 }
15980 run_test 224a "Don't panic on bulk IO failure"
15981
15982 test_224b() { # LU-1039, MRP-303
15983         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15984
15985         dd if=/dev/zero of=$DIR/$tfile bs=4096 count=1
15986         cancel_lru_locks osc
15987         #define OBD_FAIL_PTLRPC_CLIENT_BULK_CB2   0x515
15988         $LCTL set_param fail_loc=0x515
15989         dd of=/dev/null if=$DIR/$tfile bs=4096 count=1
15990         $LCTL set_param fail_loc=0
15991         df $DIR
15992 }
15993 run_test 224b "Don't panic on bulk IO failure"
15994
15995 test_224c() { # LU-6441
15996         [ $PARALLEL == "yes" ] && skip "skip parallel run"
15997         remote_mds_nodsh && skip "remote MDS with nodsh"
15998
15999         local p="$TMP/$TESTSUITE-$TESTNAME.parameters"
16000         save_writethrough $p
16001         set_cache writethrough on
16002
16003         local pages_per_rpc=$($LCTL get_param \
16004                                 osc.*.max_pages_per_rpc)
16005         local at_max=$($LCTL get_param -n at_max)
16006         local timeout=$($LCTL get_param -n timeout)
16007         local test_at="at_max"
16008         local param_at="$FSNAME.sys.at_max"
16009         local test_timeout="timeout"
16010         local param_timeout="$FSNAME.sys.timeout"
16011
16012         $LCTL set_param -n osc.*.max_pages_per_rpc=1024
16013
16014         set_persistent_param_and_check client "$test_at" "$param_at" 0
16015         set_persistent_param_and_check client "$test_timeout" "$param_timeout" 5
16016
16017         #define OBD_FAIL_PTLRPC_CLIENT_BULK_CB3 0x520
16018         do_facet ost1 "$LCTL set_param fail_loc=0x520"
16019         $LFS setstripe -c 1 -i 0 $DIR/$tfile
16020         dd if=/dev/zero of=$DIR/$tfile bs=8MB count=1
16021         sync
16022         do_facet ost1 "$LCTL set_param fail_loc=0"
16023
16024         set_persistent_param_and_check client "$test_at" "$param_at" $at_max
16025         set_persistent_param_and_check client "$test_timeout" "$param_timeout" \
16026                 $timeout
16027
16028         $LCTL set_param -n $pages_per_rpc
16029         restore_lustre_params < $p
16030         rm -f $p
16031 }
16032 run_test 224c "Don't hang if one of md lost during large bulk RPC"
16033
16034 MDSSURVEY=${MDSSURVEY:-$(which mds-survey 2>/dev/null || true)}
16035 test_225a () {
16036         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16037         if [ -z ${MDSSURVEY} ]; then
16038                 skip_env "mds-survey not found"
16039         fi
16040         [ $MDS1_VERSION -ge $(version_code 2.2.51) ] ||
16041                 skip "Need MDS version at least 2.2.51"
16042
16043         local mds=$(facet_host $SINGLEMDS)
16044         local target=$(do_nodes $mds 'lctl dl' |
16045                        awk '{ if ($2 == "UP" && $3 == "mdt") { print $4 }}')
16046
16047         local cmd1="file_count=1000 thrhi=4"
16048         local cmd2="dir_count=2 layer=mdd stripe_count=0"
16049         local cmd3="rslt_loc=${TMP} targets=\"$mds:$target\" $MDSSURVEY"
16050         local cmd="$cmd1 $cmd2 $cmd3"
16051
16052         rm -f ${TMP}/mds_survey*
16053         echo + $cmd
16054         eval $cmd || error "mds-survey with zero-stripe failed"
16055         cat ${TMP}/mds_survey*
16056         rm -f ${TMP}/mds_survey*
16057 }
16058 run_test 225a "Metadata survey sanity with zero-stripe"
16059
16060 test_225b () {
16061         if [ -z ${MDSSURVEY} ]; then
16062                 skip_env "mds-survey not found"
16063         fi
16064         [ $MDS1_VERSION -ge $(version_code 2.2.51) ] ||
16065                 skip "Need MDS version at least 2.2.51"
16066         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16067         remote_mds_nodsh && skip "remote MDS with nodsh"
16068         if [ $($LCTL dl | grep -c osc) -eq 0 ]; then
16069                 skip_env "Need to mount OST to test"
16070         fi
16071
16072         local mds=$(facet_host $SINGLEMDS)
16073         local target=$(do_nodes $mds 'lctl dl' |
16074                        awk '{ if ($2 == "UP" && $3 == "mdt") { print $4 }}')
16075
16076         local cmd1="file_count=1000 thrhi=4"
16077         local cmd2="dir_count=2 layer=mdd stripe_count=1"
16078         local cmd3="rslt_loc=${TMP} targets=\"$mds:$target\" $MDSSURVEY"
16079         local cmd="$cmd1 $cmd2 $cmd3"
16080
16081         rm -f ${TMP}/mds_survey*
16082         echo + $cmd
16083         eval $cmd || error "mds-survey with stripe_count failed"
16084         cat ${TMP}/mds_survey*
16085         rm -f ${TMP}/mds_survey*
16086 }
16087 run_test 225b "Metadata survey sanity with stripe_count = 1"
16088
16089 mcreate_path2fid () {
16090         local mode=$1
16091         local major=$2
16092         local minor=$3
16093         local name=$4
16094         local desc=$5
16095         local path=$DIR/$tdir/$name
16096         local fid
16097         local rc
16098         local fid_path
16099
16100         $MCREATE --mode=$1 --major=$2 --minor=$3 $path ||
16101                 error "cannot create $desc"
16102
16103         fid=$($LFS path2fid $path | tr -d '[' | tr -d ']')
16104         rc=$?
16105         [ $rc -ne 0 ] && error "cannot get fid of a $desc"
16106
16107         fid_path=$($LFS fid2path $MOUNT $fid)
16108         rc=$?
16109         [ $rc -ne 0 ] && error "cannot get path of $desc by $DIR $path $fid"
16110
16111         [ "$path" == "$fid_path" ] ||
16112                 error "fid2path returned $fid_path, expected $path"
16113
16114         echo "pass with $path and $fid"
16115 }
16116
16117 test_226a () {
16118         rm -rf $DIR/$tdir
16119         mkdir -p $DIR/$tdir
16120
16121         mcreate_path2fid 0010666 0 0 fifo "FIFO"
16122         mcreate_path2fid 0020666 1 3 null "character special file (null)"
16123         mcreate_path2fid 0020666 1 255 none "character special file (no device)"
16124         mcreate_path2fid 0040666 0 0 dir "directory"
16125         mcreate_path2fid 0060666 7 0 loop0 "block special file (loop)"
16126         mcreate_path2fid 0100666 0 0 file "regular file"
16127         mcreate_path2fid 0120666 0 0 link "symbolic link"
16128         mcreate_path2fid 0140666 0 0 sock "socket"
16129 }
16130 run_test 226a "call path2fid and fid2path on files of all type"
16131
16132 test_226b () {
16133         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
16134
16135         local MDTIDX=1
16136
16137         rm -rf $DIR/$tdir
16138         mkdir -p $DIR/$tdir
16139         $LFS setdirstripe -i $MDTIDX $DIR/$tdir/remote_dir ||
16140                 error "create remote directory failed"
16141         mcreate_path2fid 0010666 0 0 "remote_dir/fifo" "FIFO"
16142         mcreate_path2fid 0020666 1 3 "remote_dir/null" \
16143                                 "character special file (null)"
16144         mcreate_path2fid 0020666 1 255 "remote_dir/none" \
16145                                 "character special file (no device)"
16146         mcreate_path2fid 0040666 0 0 "remote_dir/dir" "directory"
16147         mcreate_path2fid 0060666 7 0 "remote_dir/loop0" \
16148                                 "block special file (loop)"
16149         mcreate_path2fid 0100666 0 0 "remote_dir/file" "regular file"
16150         mcreate_path2fid 0120666 0 0 "remote_dir/link" "symbolic link"
16151         mcreate_path2fid 0140666 0 0 "remote_dir/sock" "socket"
16152 }
16153 run_test 226b "call path2fid and fid2path on files of all type under remote dir"
16154
16155 # LU-1299 Executing or running ldd on a truncated executable does not
16156 # cause an out-of-memory condition.
16157 test_227() {
16158         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16159         [ -z "$(which ldd)" ] && skip_env "should have ldd tool"
16160
16161         dd if=$(which date) of=$MOUNT/date bs=1k count=1
16162         chmod +x $MOUNT/date
16163
16164         $MOUNT/date > /dev/null
16165         ldd $MOUNT/date > /dev/null
16166         rm -f $MOUNT/date
16167 }
16168 run_test 227 "running truncated executable does not cause OOM"
16169
16170 # LU-1512 try to reuse idle OI blocks
16171 test_228a() {
16172         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16173         remote_mds_nodsh && skip "remote MDS with nodsh"
16174         [ "$mds1_FSTYPE" != "ldiskfs" ] && skip_env "ldiskfs only test"
16175
16176         local MDT_DEV=$(mdsdevname ${SINGLEMDS//mds/})
16177         local myDIR=$DIR/$tdir
16178
16179         mkdir -p $myDIR
16180         #define OBD_FAIL_SEQ_EXHAUST             0x1002
16181         $LCTL set_param fail_loc=0x80001002
16182         createmany -o $myDIR/t- 10000
16183         $LCTL set_param fail_loc=0
16184         # The guard is current the largest FID holder
16185         touch $myDIR/guard
16186         local SEQ=$($LFS path2fid $myDIR/guard | awk -F ':' '{print $1}' |
16187                     tr -d '[')
16188         local IDX=$(($SEQ % 64))
16189
16190         do_facet $SINGLEMDS sync
16191         # Make sure journal flushed.
16192         sleep 6
16193         local blk1=$(do_facet $SINGLEMDS \
16194                      "$DEBUGFS -c -R \\\"stat oi.16.${IDX}\\\" $MDT_DEV" |
16195                      grep Blockcount | awk '{print $4}')
16196
16197         # Remove old files, some OI blocks will become idle.
16198         unlinkmany $myDIR/t- 10000
16199         # Create new files, idle OI blocks should be reused.
16200         createmany -o $myDIR/t- 2000
16201         do_facet $SINGLEMDS sync
16202         # Make sure journal flushed.
16203         sleep 6
16204         local blk2=$(do_facet $SINGLEMDS \
16205                      "$DEBUGFS -c -R \\\"stat oi.16.${IDX}\\\" $MDT_DEV" |
16206                      grep Blockcount | awk '{print $4}')
16207
16208         [ $blk1 == $blk2 ] || error "old blk1=$blk1, new blk2=$blk2, unmatched!"
16209 }
16210 run_test 228a "try to reuse idle OI blocks"
16211
16212 test_228b() {
16213         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16214         remote_mds_nodsh && skip "remote MDS with nodsh"
16215         [ "$mds1_FSTYPE" != "ldiskfs" ] && skip_env "ldiskfs only test"
16216
16217         local MDT_DEV=$(mdsdevname ${SINGLEMDS//mds/})
16218         local myDIR=$DIR/$tdir
16219
16220         mkdir -p $myDIR
16221         #define OBD_FAIL_SEQ_EXHAUST             0x1002
16222         $LCTL set_param fail_loc=0x80001002
16223         createmany -o $myDIR/t- 10000
16224         $LCTL set_param fail_loc=0
16225         # The guard is current the largest FID holder
16226         touch $myDIR/guard
16227         local SEQ=$($LFS path2fid $myDIR/guard | awk -F ':' '{print $1}' |
16228                     tr -d '[')
16229         local IDX=$(($SEQ % 64))
16230
16231         do_facet $SINGLEMDS sync
16232         # Make sure journal flushed.
16233         sleep 6
16234         local blk1=$(do_facet $SINGLEMDS \
16235                      "$DEBUGFS -c -R \\\"stat oi.16.${IDX}\\\" $MDT_DEV" |
16236                      grep Blockcount | awk '{print $4}')
16237
16238         # Remove old files, some OI blocks will become idle.
16239         unlinkmany $myDIR/t- 10000
16240
16241         # stop the MDT
16242         stop $SINGLEMDS || error "Fail to stop MDT."
16243         # remount the MDT
16244         start $SINGLEMDS $MDT_DEV $MDS_MOUNT_OPTS || error "Fail to start MDT."
16245
16246         df $MOUNT || error "Fail to df."
16247         # Create new files, idle OI blocks should be reused.
16248         createmany -o $myDIR/t- 2000
16249         do_facet $SINGLEMDS sync
16250         # Make sure journal flushed.
16251         sleep 6
16252         local blk2=$(do_facet $SINGLEMDS \
16253                      "$DEBUGFS -c -R \\\"stat oi.16.${IDX}\\\" $MDT_DEV" |
16254                      grep Blockcount | awk '{print $4}')
16255
16256         [ $blk1 == $blk2 ] || error "old blk1=$blk1, new blk2=$blk2, unmatched!"
16257 }
16258 run_test 228b "idle OI blocks can be reused after MDT restart"
16259
16260 #LU-1881
16261 test_228c() {
16262         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16263         remote_mds_nodsh && skip "remote MDS with nodsh"
16264         [ "$mds1_FSTYPE" != "ldiskfs" ] && skip_env "ldiskfs only test"
16265
16266         local MDT_DEV=$(mdsdevname ${SINGLEMDS//mds/})
16267         local myDIR=$DIR/$tdir
16268
16269         mkdir -p $myDIR
16270         #define OBD_FAIL_SEQ_EXHAUST             0x1002
16271         $LCTL set_param fail_loc=0x80001002
16272         # 20000 files can guarantee there are index nodes in the OI file
16273         createmany -o $myDIR/t- 20000
16274         $LCTL set_param fail_loc=0
16275         # The guard is current the largest FID holder
16276         touch $myDIR/guard
16277         local SEQ=$($LFS path2fid $myDIR/guard | awk -F ':' '{print $1}' |
16278                     tr -d '[')
16279         local IDX=$(($SEQ % 64))
16280
16281         do_facet $SINGLEMDS sync
16282         # Make sure journal flushed.
16283         sleep 6
16284         local blk1=$(do_facet $SINGLEMDS \
16285                      "$DEBUGFS -c -R \\\"stat oi.16.${IDX}\\\" $MDT_DEV" |
16286                      grep Blockcount | awk '{print $4}')
16287
16288         # Remove old files, some OI blocks will become idle.
16289         unlinkmany $myDIR/t- 20000
16290         rm -f $myDIR/guard
16291         # The OI file should become empty now
16292
16293         # Create new files, idle OI blocks should be reused.
16294         createmany -o $myDIR/t- 2000
16295         do_facet $SINGLEMDS sync
16296         # Make sure journal flushed.
16297         sleep 6
16298         local blk2=$(do_facet $SINGLEMDS \
16299                      "$DEBUGFS -c -R \\\"stat oi.16.${IDX}\\\" $MDT_DEV" |
16300                      grep Blockcount | awk '{print $4}')
16301
16302         [ $blk1 == $blk2 ] || error "old blk1=$blk1, new blk2=$blk2, unmatched!"
16303 }
16304 run_test 228c "NOT shrink the last entry in OI index node to recycle idle leaf"
16305
16306 test_229() { # LU-2482, LU-3448
16307         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16308         [ $OSTCOUNT -lt 2 ] && skip_env "needs >= 2 OSTs"
16309         [ $MDS1_VERSION -lt $(version_code 2.4.53) ] &&
16310                 skip "No HSM $(lustre_build_version $SINGLEMDS) MDS < 2.4.53"
16311
16312         rm -f $DIR/$tfile
16313
16314         # Create a file with a released layout and stripe count 2.
16315         $MULTIOP $DIR/$tfile H2c ||
16316                 error "failed to create file with released layout"
16317
16318         $LFS getstripe -v $DIR/$tfile
16319
16320         local pattern=$($LFS getstripe -L $DIR/$tfile)
16321         [ X"$pattern" = X"released" ] || error "pattern error ($pattern)"
16322
16323         local stripe_count=$($LFS getstripe -c $DIR/$tfile) ||
16324                 error "getstripe"
16325         [ $stripe_count -eq 2 ] || error "stripe count not 2 ($stripe_count)"
16326         stat $DIR/$tfile || error "failed to stat released file"
16327
16328         chown $RUNAS_ID $DIR/$tfile ||
16329                 error "chown $RUNAS_ID $DIR/$tfile failed"
16330
16331         chgrp $RUNAS_ID $DIR/$tfile ||
16332                 error "chgrp $RUNAS_ID $DIR/$tfile failed"
16333
16334         touch $DIR/$tfile || error "touch $DIR/$tfile failed"
16335         rm $DIR/$tfile || error "failed to remove released file"
16336 }
16337 run_test 229 "getstripe/stat/rm/attr changes work on released files"
16338
16339 test_230a() {
16340         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16341         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
16342         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
16343                 skip "Need MDS version at least 2.11.52"
16344
16345         local MDTIDX=1
16346
16347         test_mkdir $DIR/$tdir
16348         test_mkdir -i0 -c1 $DIR/$tdir/test_230_local
16349         local mdt_idx=$($LFS getstripe -m $DIR/$tdir/test_230_local)
16350         [ $mdt_idx -ne 0 ] &&
16351                 error "create local directory on wrong MDT $mdt_idx"
16352
16353         $LFS mkdir -i $MDTIDX $DIR/$tdir/test_230 ||
16354                         error "create remote directory failed"
16355         local mdt_idx=$($LFS getstripe -m $DIR/$tdir/test_230)
16356         [ $mdt_idx -ne $MDTIDX ] &&
16357                 error "create remote directory on wrong MDT $mdt_idx"
16358
16359         createmany -o $DIR/$tdir/test_230/t- 10 ||
16360                 error "create files on remote directory failed"
16361         mdt_idx=$($LFS getstripe -m $DIR/$tdir/test_230/t-0)
16362         [ $mdt_idx -ne $MDTIDX ] && error "create files on wrong MDT $mdt_idx"
16363         rm -r $DIR/$tdir || error "unlink remote directory failed"
16364 }
16365 run_test 230a "Create remote directory and files under the remote directory"
16366
16367 test_230b() {
16368         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16369         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
16370         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
16371                 skip "Need MDS version at least 2.11.52"
16372
16373         local MDTIDX=1
16374         local mdt_index
16375         local i
16376         local file
16377         local pid
16378         local stripe_count
16379         local migrate_dir=$DIR/$tdir/migrate_dir
16380         local other_dir=$DIR/$tdir/other_dir
16381
16382         test_mkdir $DIR/$tdir
16383         test_mkdir -i0 -c1 $migrate_dir
16384         test_mkdir -i0 -c1 $other_dir
16385         for ((i=0; i<10; i++)); do
16386                 mkdir -p $migrate_dir/dir_${i}
16387                 createmany -o $migrate_dir/dir_${i}/f 10 ||
16388                         error "create files under remote dir failed $i"
16389         done
16390
16391         cp /etc/passwd $migrate_dir/$tfile
16392         cp /etc/passwd $other_dir/$tfile
16393         chattr +SAD $migrate_dir
16394         chattr +SAD $migrate_dir/$tfile
16395
16396         local old_dir_flag=$(lsattr -a $migrate_dir | awk '/\/\.$/ {print $1}')
16397         local old_file_flag=$(lsattr $migrate_dir/$tfile | awk '{print $1}')
16398         local old_dir_mode=$(stat -c%f $migrate_dir)
16399         local old_file_mode=$(stat -c%f $migrate_dir/$tfile)
16400
16401         mkdir -p $migrate_dir/dir_default_stripe2
16402         $LFS setstripe -c 2 $migrate_dir/dir_default_stripe2
16403         $LFS setstripe -c 2 $migrate_dir/${tfile}_stripe2
16404
16405         mkdir -p $other_dir
16406         ln $migrate_dir/$tfile $other_dir/luna
16407         ln $migrate_dir/$tfile $migrate_dir/sofia
16408         ln $other_dir/$tfile $migrate_dir/david
16409         ln -s $migrate_dir/$tfile $other_dir/zachary
16410         ln -s $migrate_dir/$tfile $migrate_dir/${tfile}_ln
16411         ln -s $other_dir/$tfile $migrate_dir/${tfile}_ln_other
16412
16413         $LFS migrate -m $MDTIDX $migrate_dir ||
16414                 error "fails on migrating remote dir to MDT1"
16415
16416         echo "migratate to MDT1, then checking.."
16417         for ((i = 0; i < 10; i++)); do
16418                 for file in $(find $migrate_dir/dir_${i}); do
16419                         mdt_index=$($LFS getstripe -m $file)
16420                         [ $mdt_index == $MDTIDX ] ||
16421                                 error "$file is not on MDT${MDTIDX}"
16422                 done
16423         done
16424
16425         # the multiple link file should still in MDT0
16426         mdt_index=$($LFS getstripe -m $migrate_dir/$tfile)
16427         [ $mdt_index == 0 ] ||
16428                 error "$file is not on MDT${MDTIDX}"
16429
16430         local new_dir_flag=$(lsattr -a $migrate_dir | awk '/\/\.$/ {print $1}')
16431         [ "$old_dir_flag" = "$new_dir_flag" ] ||
16432                 error " expect $old_dir_flag get $new_dir_flag"
16433
16434         local new_file_flag=$(lsattr $migrate_dir/$tfile | awk '{print $1}')
16435         [ "$old_file_flag" = "$new_file_flag" ] ||
16436                 error " expect $old_file_flag get $new_file_flag"
16437
16438         local new_dir_mode=$(stat -c%f $migrate_dir)
16439         [ "$old_dir_mode" = "$new_dir_mode" ] ||
16440                 error "expect mode $old_dir_mode get $new_dir_mode"
16441
16442         local new_file_mode=$(stat -c%f $migrate_dir/$tfile)
16443         [ "$old_file_mode" = "$new_file_mode" ] ||
16444                 error "expect mode $old_file_mode get $new_file_mode"
16445
16446         diff /etc/passwd $migrate_dir/$tfile ||
16447                 error "$tfile different after migration"
16448
16449         diff /etc/passwd $other_dir/luna ||
16450                 error "luna different after migration"
16451
16452         diff /etc/passwd $migrate_dir/sofia ||
16453                 error "sofia different after migration"
16454
16455         diff /etc/passwd $migrate_dir/david ||
16456                 error "david different after migration"
16457
16458         diff /etc/passwd $other_dir/zachary ||
16459                 error "zachary different after migration"
16460
16461         diff /etc/passwd $migrate_dir/${tfile}_ln ||
16462                 error "${tfile}_ln different after migration"
16463
16464         diff /etc/passwd $migrate_dir/${tfile}_ln_other ||
16465                 error "${tfile}_ln_other different after migration"
16466
16467         stripe_count=$($LFS getstripe -c $migrate_dir/dir_default_stripe2)
16468         [ $stripe_count = 2 ] ||
16469                 error "dir strpe_count $d != 2 after migration."
16470
16471         stripe_count=$($LFS getstripe -c $migrate_dir/${tfile}_stripe2)
16472         [ $stripe_count = 2 ] ||
16473                 error "file strpe_count $d != 2 after migration."
16474
16475         #migrate back to MDT0
16476         MDTIDX=0
16477
16478         $LFS migrate -m $MDTIDX $migrate_dir ||
16479                 error "fails on migrating remote dir to MDT0"
16480
16481         echo "migrate back to MDT0, checking.."
16482         for file in $(find $migrate_dir); do
16483                 mdt_index=$($LFS getstripe -m $file)
16484                 [ $mdt_index == $MDTIDX ] ||
16485                         error "$file is not on MDT${MDTIDX}"
16486         done
16487
16488         local new_dir_flag=$(lsattr -a $migrate_dir | awk '/\/\.$/ {print $1}')
16489         [ "$old_dir_flag" = "$new_dir_flag" ] ||
16490                 error " expect $old_dir_flag get $new_dir_flag"
16491
16492         local new_file_flag=$(lsattr $migrate_dir/$tfile | awk '{print $1}')
16493         [ "$old_file_flag" = "$new_file_flag" ] ||
16494                 error " expect $old_file_flag get $new_file_flag"
16495
16496         local new_dir_mode=$(stat -c%f $migrate_dir)
16497         [ "$old_dir_mode" = "$new_dir_mode" ] ||
16498                 error "expect mode $old_dir_mode get $new_dir_mode"
16499
16500         local new_file_mode=$(stat -c%f $migrate_dir/$tfile)
16501         [ "$old_file_mode" = "$new_file_mode" ] ||
16502                 error "expect mode $old_file_mode get $new_file_mode"
16503
16504         diff /etc/passwd ${migrate_dir}/$tfile ||
16505                 error "$tfile different after migration"
16506
16507         diff /etc/passwd ${other_dir}/luna ||
16508                 error "luna different after migration"
16509
16510         diff /etc/passwd ${migrate_dir}/sofia ||
16511                 error "sofia different after migration"
16512
16513         diff /etc/passwd ${other_dir}/zachary ||
16514                 error "zachary different after migration"
16515
16516         diff /etc/passwd $migrate_dir/${tfile}_ln ||
16517                 error "${tfile}_ln different after migration"
16518
16519         diff /etc/passwd $migrate_dir/${tfile}_ln_other ||
16520                 error "${tfile}_ln_other different after migration"
16521
16522         stripe_count=$($LFS getstripe -c ${migrate_dir}/dir_default_stripe2)
16523         [ $stripe_count = 2 ] ||
16524                 error "dir strpe_count $d != 2 after migration."
16525
16526         stripe_count=$($LFS getstripe -c ${migrate_dir}/${tfile}_stripe2)
16527         [ $stripe_count = 2 ] ||
16528                 error "file strpe_count $d != 2 after migration."
16529
16530         rm -rf $DIR/$tdir || error "rm dir failed after migration"
16531 }
16532 run_test 230b "migrate directory"
16533
16534 test_230c() {
16535         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16536         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
16537         remote_mds_nodsh && skip "remote MDS with nodsh"
16538         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
16539                 skip "Need MDS version at least 2.11.52"
16540
16541         local MDTIDX=1
16542         local total=3
16543         local mdt_index
16544         local file
16545         local migrate_dir=$DIR/$tdir/migrate_dir
16546
16547         #If migrating directory fails in the middle, all entries of
16548         #the directory is still accessiable.
16549         test_mkdir $DIR/$tdir
16550         test_mkdir -i0 -c1 $migrate_dir
16551         test_mkdir -i1 -c1 $DIR/$tdir/remote_dir
16552         stat $migrate_dir
16553         createmany -o $migrate_dir/f $total ||
16554                 error "create files under ${migrate_dir} failed"
16555
16556         # fail after migrating top dir, and this will fail only once, so the
16557         # first sub file migration will fail (currently f3), others succeed.
16558         #OBD_FAIL_MIGRATE_ENTRIES       0x1801
16559         do_facet mds1 lctl set_param fail_loc=0x1801
16560         local t=$(ls $migrate_dir | wc -l)
16561         $LFS migrate --mdt-index $MDTIDX $migrate_dir &&
16562                 error "migrate should fail"
16563         local u=$(ls $migrate_dir | wc -l)
16564         [ "$u" == "$t" ] || error "$u != $t during migration"
16565
16566         # add new dir/file should succeed
16567         mkdir $migrate_dir/dir ||
16568                 error "mkdir failed under migrating directory"
16569         touch $migrate_dir/file ||
16570                 error "create file failed under migrating directory"
16571
16572         # add file with existing name should fail
16573         for file in $migrate_dir/f*; do
16574                 stat $file > /dev/null || error "stat $file failed"
16575                 $OPENFILE -f O_CREAT:O_EXCL $file &&
16576                         error "open(O_CREAT|O_EXCL) $file should fail"
16577                 $MULTIOP $file m && error "create $file should fail"
16578                 touch $DIR/$tdir/remote_dir/$tfile ||
16579                         error "touch $tfile failed"
16580                 ln $DIR/$tdir/remote_dir/$tfile $file &&
16581                         error "link $file should fail"
16582                 mdt_index=$($LFS getstripe -m $file)
16583                 if [ $mdt_index == 0 ]; then
16584                         # file failed to migrate is not allowed to rename to
16585                         mv $DIR/$tdir/remote_dir/$tfile $file &&
16586                                 error "rename to $file should fail"
16587                 else
16588                         mv $DIR/$tdir/remote_dir/$tfile $file ||
16589                                 error "rename to $file failed"
16590                 fi
16591                 echo hello >> $file || error "write $file failed"
16592         done
16593
16594         # resume migration with different options should fail
16595         $LFS migrate -m 0 $migrate_dir &&
16596                 error "migrate -m 0 $migrate_dir should fail"
16597
16598         $LFS migrate -m $MDTIDX -c 2 $migrate_dir &&
16599                 error "migrate -c 2 $migrate_dir should fail"
16600
16601         # resume migration should succeed
16602         $LFS migrate -m $MDTIDX $migrate_dir ||
16603                 error "migrate $migrate_dir failed"
16604
16605         echo "Finish migration, then checking.."
16606         for file in $(find $migrate_dir); do
16607                 mdt_index=$($LFS getstripe -m $file)
16608                 [ $mdt_index == $MDTIDX ] ||
16609                         error "$file is not on MDT${MDTIDX}"
16610         done
16611
16612         rm -rf $DIR/$tdir || error "rm dir failed after migration"
16613 }
16614 run_test 230c "check directory accessiblity if migration failed"
16615
16616 test_230d() {
16617         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16618         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
16619         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
16620                 skip "Need MDS version at least 2.11.52"
16621         # LU-11235
16622         [ "$mds1_FSTYPE" == "zfs" ] && skip "skip ZFS backend"
16623
16624         local migrate_dir=$DIR/$tdir/migrate_dir
16625         local old_index
16626         local new_index
16627         local old_count
16628         local new_count
16629         local new_hash
16630         local mdt_index
16631         local i
16632         local j
16633
16634         old_index=$((RANDOM % MDSCOUNT))
16635         old_count=$((MDSCOUNT - old_index))
16636         new_index=$((RANDOM % MDSCOUNT))
16637         new_count=$((MDSCOUNT - new_index))
16638         new_hash="all_char"
16639
16640         [ $old_count -gt 1 ] && old_count=$((old_count - RANDOM % old_count))
16641         [ $new_count -gt 1 ] && new_count=$((new_count - RANDOM % new_count))
16642
16643         test_mkdir $DIR/$tdir
16644         test_mkdir -i $old_index -c $old_count $migrate_dir
16645
16646         for ((i=0; i<100; i++)); do
16647                 test_mkdir -i0 -c1 $migrate_dir/dir_${i}
16648                 createmany -o $migrate_dir/dir_${i}/f 100 ||
16649                         error "create files under remote dir failed $i"
16650         done
16651
16652         echo -n "Migrate from MDT$old_index "
16653         [ $old_count -gt 1 ] && echo -n "... MDT$((old_index + old_count - 1)) "
16654         echo -n "to MDT$new_index"
16655         [ $new_count -gt 1 ] && echo -n " ... MDT$((new_index + new_count - 1))"
16656         echo
16657
16658         echo "$LFS migrate -m$new_index -c$new_count -H $new_hash $migrate_dir"
16659         $LFS migrate -m $new_index -c $new_count -H $new_hash $migrate_dir ||
16660                 error "migrate remote dir error"
16661
16662         echo "Finish migration, then checking.."
16663         for file in $(find $migrate_dir); do
16664                 mdt_index=$($LFS getstripe -m $file)
16665                 if [ $mdt_index -lt $new_index ] ||
16666                    [ $mdt_index -gt $((new_index + new_count - 1)) ]; then
16667                         error "$file is on MDT$mdt_index"
16668                 fi
16669         done
16670
16671         rm -rf $DIR/$tdir || error "rm dir failed after migration"
16672 }
16673 run_test 230d "check migrate big directory"
16674
16675 test_230e() {
16676         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16677         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
16678         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
16679                 skip "Need MDS version at least 2.11.52"
16680
16681         local i
16682         local j
16683         local a_fid
16684         local b_fid
16685
16686         mkdir -p $DIR/$tdir
16687         mkdir $DIR/$tdir/migrate_dir
16688         mkdir $DIR/$tdir/other_dir
16689         touch $DIR/$tdir/migrate_dir/a
16690         ln $DIR/$tdir/migrate_dir/a $DIR/$tdir/other_dir/b
16691         ls $DIR/$tdir/other_dir
16692
16693         $LFS migrate -m 1 $DIR/$tdir/migrate_dir ||
16694                 error "migrate dir fails"
16695
16696         mdt_index=$($LFS getstripe -m $DIR/$tdir/migrate_dir)
16697         [ $mdt_index == 1 ] || error "migrate_dir is not on MDT1"
16698
16699         mdt_index=$($LFS getstripe -m $DIR/$tdir/migrate_dir/a)
16700         [ $mdt_index == 0 ] || error "a is not on MDT0"
16701
16702         $LFS migrate -m 1 $DIR/$tdir/other_dir ||
16703                 error "migrate dir fails"
16704
16705         mdt_index=$($LFS getstripe -m $DIR/$tdir/other_dir)
16706         [ $mdt_index == 1 ] || error "other_dir is not on MDT1"
16707
16708         mdt_index=$($LFS getstripe -m $DIR/$tdir/migrate_dir/a)
16709         [ $mdt_index == 1 ] || error "a is not on MDT1"
16710
16711         mdt_index=$($LFS getstripe -m $DIR/$tdir/other_dir/b)
16712         [ $mdt_index == 1 ] || error "b is not on MDT1"
16713
16714         a_fid=$($LFS path2fid $DIR/$tdir/migrate_dir/a)
16715         b_fid=$($LFS path2fid $DIR/$tdir/other_dir/b)
16716
16717         [ "$a_fid" = "$b_fid" ] || error "different fid after migration"
16718
16719         rm -rf $DIR/$tdir || error "rm dir failed after migration"
16720 }
16721 run_test 230e "migrate mulitple local link files"
16722
16723 test_230f() {
16724         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16725         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
16726         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
16727                 skip "Need MDS version at least 2.11.52"
16728
16729         local a_fid
16730         local ln_fid
16731
16732         mkdir -p $DIR/$tdir
16733         mkdir $DIR/$tdir/migrate_dir
16734         $LFS mkdir -i1 $DIR/$tdir/other_dir
16735         touch $DIR/$tdir/migrate_dir/a
16736         ln $DIR/$tdir/migrate_dir/a $DIR/$tdir/other_dir/ln1
16737         ln $DIR/$tdir/migrate_dir/a $DIR/$tdir/other_dir/ln2
16738         ls $DIR/$tdir/other_dir
16739
16740         # a should be migrated to MDT1, since no other links on MDT0
16741         $LFS migrate -m 1 $DIR/$tdir/migrate_dir ||
16742                 error "#1 migrate dir fails"
16743         mdt_index=$($LFS getstripe -m $DIR/$tdir/migrate_dir)
16744         [ $mdt_index == 1 ] || error "migrate_dir is not on MDT1"
16745         mdt_index=$($LFS getstripe -m $DIR/$tdir/migrate_dir/a)
16746         [ $mdt_index == 1 ] || error "a is not on MDT1"
16747
16748         # a should stay on MDT1, because it is a mulitple link file
16749         $LFS migrate -m 0 $DIR/$tdir/migrate_dir ||
16750                 error "#2 migrate dir fails"
16751         mdt_index=$($LFS getstripe -m $DIR/$tdir/migrate_dir/a)
16752         [ $mdt_index == 1 ] || error "a is not on MDT1"
16753
16754         $LFS migrate -m 1 $DIR/$tdir/migrate_dir ||
16755                 error "#3 migrate dir fails"
16756
16757         a_fid=$($LFS path2fid $DIR/$tdir/migrate_dir/a)
16758         ln_fid=$($LFS path2fid $DIR/$tdir/other_dir/ln1)
16759         [ "$a_fid" = "$ln_fid" ] || error "different fid after migrate to MDT1"
16760
16761         rm -rf $DIR/$tdir/other_dir/ln1 || error "unlink ln1 fails"
16762         rm -rf $DIR/$tdir/other_dir/ln2 || error "unlink ln2 fails"
16763
16764         # a should be migrated to MDT0, since no other links on MDT1
16765         $LFS migrate -m 0 $DIR/$tdir/migrate_dir ||
16766                 error "#4 migrate dir fails"
16767         mdt_index=$($LFS getstripe -m $DIR/$tdir/migrate_dir/a)
16768         [ $mdt_index == 0 ] || error "a is not on MDT0"
16769
16770         rm -rf $DIR/$tdir || error "rm dir failed after migration"
16771 }
16772 run_test 230f "migrate mulitple remote link files"
16773
16774 test_230g() {
16775         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16776         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
16777         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
16778                 skip "Need MDS version at least 2.11.52"
16779
16780         mkdir -p $DIR/$tdir/migrate_dir
16781
16782         $LFS migrate -m 1000 $DIR/$tdir/migrate_dir &&
16783                 error "migrating dir to non-exist MDT succeeds"
16784         true
16785 }
16786 run_test 230g "migrate dir to non-exist MDT"
16787
16788 test_230h() {
16789         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16790         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
16791         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
16792                 skip "Need MDS version at least 2.11.52"
16793
16794         local mdt_index
16795
16796         mkdir -p $DIR/$tdir/migrate_dir
16797
16798         $LFS migrate -m1 $DIR &&
16799                 error "migrating mountpoint1 should fail"
16800
16801         $LFS migrate -m1 $DIR/$tdir/.. &&
16802                 error "migrating mountpoint2 should fail"
16803
16804         # same as mv
16805         $LFS migrate -m1 $DIR/$tdir/migrate_dir/.. &&
16806                 error "migrating $tdir/migrate_dir/.. should fail"
16807
16808         true
16809 }
16810 run_test 230h "migrate .. and root"
16811
16812 test_230i() {
16813         [ $PARALLEL == "yes" ] && skip "skip parallel run"
16814         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
16815         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
16816                 skip "Need MDS version at least 2.11.52"
16817
16818         mkdir -p $DIR/$tdir/migrate_dir
16819
16820         $LFS migrate -m 1 $DIR/$tdir/migrate_dir/ ||
16821                 error "migration fails with a tailing slash"
16822
16823         $LFS migrate -m 0 $DIR/$tdir/migrate_dir// ||
16824                 error "migration fails with two tailing slashes"
16825 }
16826 run_test 230i "lfs migrate -m tolerates trailing slashes"
16827
16828 test_230j() {
16829         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs"
16830         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
16831                 skip "Need MDS version at least 2.11.52"
16832
16833         $LFS mkdir -m 0 -c 1 $DIR/$tdir || error "mkdir $tdir failed"
16834         $LFS setstripe -E 1M -L mdt $DIR/$tdir/$tfile ||
16835                 error "create $tfile failed"
16836         cat /etc/passwd > $DIR/$tdir/$tfile
16837
16838         $LFS migrate -m 1 $DIR/$tdir
16839
16840         cmp /etc/passwd $DIR/$tdir/$tfile ||
16841                 error "DoM file mismatch after migration"
16842 }
16843 run_test 230j "DoM file data not changed after dir migration"
16844
16845 test_230k() {
16846         [ $MDSCOUNT -lt 4 ] && skip "needs >= 4 MDTs"
16847         [ $MDS1_VERSION -lt $(version_code 2.11.56) ] &&
16848                 skip "Need MDS version at least 2.11.56"
16849
16850         local total=20
16851         local files_on_starting_mdt=0
16852
16853         $LFS mkdir -i -1 -c 2 $DIR/$tdir || error "mkdir failed"
16854         $LFS getdirstripe $DIR/$tdir
16855         for i in $(seq $total); do
16856                 echo $((i*i - i)) > $DIR/$tdir/$tfile.$i || error "write failed"
16857                 [[ $($LFS getstripe -m $DIR/$tdir/$tfile.$i) -eq 0 ]] &&
16858                         files_on_starting_mdt=$((files_on_starting_mdt + 1))
16859         done
16860
16861         echo "$files_on_starting_mdt files on MDT0"
16862
16863         $LFS migrate -m 1,3 $DIR/$tdir || error "migrate -m 1,3 failed"
16864         $LFS getdirstripe $DIR/$tdir
16865
16866         files_on_starting_mdt=0
16867         for i in $(seq $total); do
16868                 $(echo $((i*i - i)) | cmp $DIR/$tdir/$tfile.$i -) ||
16869                         error "file $tfile.$i mismatch after migration"
16870                 [[ $($LFS getstripe -m $DIR/$tdir/$tfile.$i) -eq 1 ]] &&
16871                         files_on_starting_mdt=$((files_on_starting_mdt + 1))
16872         done
16873
16874         echo "$files_on_starting_mdt files on MDT1 after migration"
16875         [[ $files_on_starting_mdt -eq $total ]] && error "all files on MDT1"
16876
16877         $LFS migrate -m 0 -c 2 $DIR/$tdir || error "migrate -m 0 -c 2 failed"
16878         $LFS getdirstripe $DIR/$tdir
16879
16880         files_on_starting_mdt=0
16881         for i in $(seq $total); do
16882                 $(echo $((i*i - i)) | cmp $DIR/$tdir/$tfile.$i -) ||
16883                         error "file $tfile.$i mismatch after 2nd migration"
16884                 [[ $($LFS getstripe -m $DIR/$tdir/$tfile.$i) -eq 0 ]] &&
16885                         files_on_starting_mdt=$((files_on_starting_mdt + 1))
16886         done
16887
16888         echo "$files_on_starting_mdt files on MDT0 after 2nd migration"
16889         [[ $files_on_starting_mdt -eq $total ]] && error "all files on MDT0"
16890
16891         true
16892 }
16893 run_test 230k "file data not changed after dir migration"
16894
16895 test_230l() {
16896         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs"
16897         [ $MDS1_VERSION -lt $(version_code 2.11.56) ] &&
16898                 skip "Need MDS version at least 2.11.56"
16899
16900         $LFS mkdir -i 0 -c 1 $DIR/$tdir || error "mkdir failed"
16901         createmany -o $DIR/$tdir/f___________________________________ 1000 ||
16902                 error "create files under remote dir failed $i"
16903         $LFS migrate -m 1 $DIR/$tdir || error "migrate failed"
16904 }
16905 run_test 230l "readdir between MDTs won't crash"
16906
16907 test_231a()
16908 {
16909         # For simplicity this test assumes that max_pages_per_rpc
16910         # is the same across all OSCs
16911         local max_pages=$($LCTL get_param -n osc.*.max_pages_per_rpc | head -n1)
16912         local bulk_size=$((max_pages * PAGE_SIZE))
16913         local brw_size=$(do_facet ost1 $LCTL get_param -n obdfilter.*.brw_size |
16914                                        head -n 1)
16915
16916         mkdir -p $DIR/$tdir
16917         $LFS setstripe -S ${brw_size}M $DIR/$tdir ||
16918                 error "failed to set stripe with -S ${brw_size}M option"
16919
16920         # clear the OSC stats
16921         $LCTL set_param osc.*.stats=0 &>/dev/null
16922         stop_writeback
16923
16924         # Client writes $bulk_size - there must be 1 rpc for $max_pages.
16925         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=$bulk_size count=1 \
16926                 oflag=direct &>/dev/null || error "dd failed"
16927
16928         sync; sleep 1; sync # just to be safe
16929         local nrpcs=$($LCTL get_param osc.*.stats |awk '/ost_write/ {print $2}')
16930         if [ x$nrpcs != "x1" ]; then
16931                 $LCTL get_param osc.*.stats
16932                 error "found $nrpcs ost_write RPCs, not 1 as expected"
16933         fi
16934
16935         start_writeback
16936         # Drop the OSC cache, otherwise we will read from it
16937         cancel_lru_locks osc
16938
16939         # clear the OSC stats
16940         $LCTL set_param osc.*.stats=0 &>/dev/null
16941
16942         # Client reads $bulk_size.
16943         dd if=$DIR/$tdir/$tfile of=/dev/null bs=$bulk_size count=1 \
16944                 iflag=direct &>/dev/null || error "dd failed"
16945
16946         nrpcs=$($LCTL get_param osc.*.stats | awk '/ost_read/ { print $2 }')
16947         if [ x$nrpcs != "x1" ]; then
16948                 $LCTL get_param osc.*.stats
16949                 error "found $nrpcs ost_read RPCs, not 1 as expected"
16950         fi
16951 }
16952 run_test 231a "checking that reading/writing of BRW RPC size results in one RPC"
16953
16954 test_231b() {
16955         mkdir -p $DIR/$tdir
16956         local i
16957         for i in {0..1023}; do
16958                 dd if=/dev/zero of=$DIR/$tdir/$tfile conv=notrunc \
16959                         seek=$((2 * i)) bs=4096 count=1 &>/dev/null ||
16960                         error "dd of=$DIR/$tdir/$tfile seek=$((2 * i)) failed"
16961         done
16962         sync
16963 }
16964 run_test 231b "must not assert on fully utilized OST request buffer"
16965
16966 test_232a() {
16967         mkdir -p $DIR/$tdir
16968         $LFS setstripe -c1 -i0 $DIR/$tdir/$tfile
16969
16970         #define OBD_FAIL_LDLM_OST_LVB            0x31c
16971         do_facet ost1 $LCTL set_param fail_loc=0x31c
16972
16973         # ignore dd failure
16974         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=1 || true
16975
16976         do_facet ost1 $LCTL set_param fail_loc=0
16977         umount_client $MOUNT || error "umount failed"
16978         mount_client $MOUNT || error "mount failed"
16979         stop ost1 || error "cannot stop ost1"
16980         start ost1 $(ostdevname 1) $OST_MOUNT_OPTS || error "cannot start ost1"
16981 }
16982 run_test 232a "failed lock should not block umount"
16983
16984 test_232b() {
16985         [ $MDS1_VERSION -ge $(version_code 2.10.58) ] ||
16986                 skip "Need MDS version at least 2.10.58"
16987
16988         mkdir -p $DIR/$tdir
16989         $LFS setstripe -c1 -i0 $DIR/$tdir/$tfile
16990         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=1
16991         sync
16992         cancel_lru_locks osc
16993
16994         #define OBD_FAIL_LDLM_OST_LVB            0x31c
16995         do_facet ost1 $LCTL set_param fail_loc=0x31c
16996
16997         # ignore failure
16998         $LFS data_version $DIR/$tdir/$tfile || true
16999
17000         do_facet ost1 $LCTL set_param fail_loc=0
17001         umount_client $MOUNT || error "umount failed"
17002         mount_client $MOUNT || error "mount failed"
17003         stop ost1 || error "cannot stop ost1"
17004         start ost1 $(ostdevname 1) $OST_MOUNT_OPTS || error "cannot start ost1"
17005 }
17006 run_test 232b "failed data version lock should not block umount"
17007
17008 test_233a() {
17009         [ $MDS1_VERSION -ge $(version_code 2.3.64) ] ||
17010                 skip "Need MDS version at least 2.3.64"
17011         [ -n "$FILESET" ] && skip_env "SKIP due to FILESET set"
17012
17013         local fid=$($LFS path2fid $MOUNT)
17014
17015         stat $MOUNT/.lustre/fid/$fid > /dev/null ||
17016                 error "cannot access $MOUNT using its FID '$fid'"
17017 }
17018 run_test 233a "checking that OBF of the FS root succeeds"
17019
17020 test_233b() {
17021         [ $MDS1_VERSION -ge $(version_code 2.5.90) ] ||
17022                 skip "Need MDS version at least 2.5.90"
17023         [ -n "$FILESET" ] && skip_env "SKIP due to FILESET set"
17024
17025         local fid=$($LFS path2fid $MOUNT/.lustre)
17026
17027         stat $MOUNT/.lustre/fid/$fid > /dev/null ||
17028                 error "cannot access $MOUNT/.lustre using its FID '$fid'"
17029
17030         fid=$($LFS path2fid $MOUNT/.lustre/fid)
17031         stat $MOUNT/.lustre/fid/$fid > /dev/null ||
17032                 error "cannot access $MOUNT/.lustre/fid using its FID '$fid'"
17033 }
17034 run_test 233b "checking that OBF of the FS .lustre succeeds"
17035
17036 test_234() {
17037         local p="$TMP/sanityN-$TESTNAME.parameters"
17038         save_lustre_params client "llite.*.xattr_cache" > $p
17039         lctl set_param llite.*.xattr_cache 1 ||
17040                 skip_env "xattr cache is not supported"
17041
17042         mkdir -p $DIR/$tdir || error "mkdir failed"
17043         touch $DIR/$tdir/$tfile || error "touch failed"
17044         # OBD_FAIL_LLITE_XATTR_ENOMEM
17045         $LCTL set_param fail_loc=0x1405
17046         getfattr -n user.attr $DIR/$tdir/$tfile &&
17047                 error "getfattr should have failed with ENOMEM"
17048         $LCTL set_param fail_loc=0x0
17049         rm -rf $DIR/$tdir
17050
17051         restore_lustre_params < $p
17052         rm -f $p
17053 }
17054 run_test 234 "xattr cache should not crash on ENOMEM"
17055
17056 test_235() {
17057         [ $MDS1_VERSION -lt $(version_code 2.4.52) ] &&
17058                 skip "Need MDS version at least 2.4.52"
17059
17060         flock_deadlock $DIR/$tfile
17061         local RC=$?
17062         case $RC in
17063                 0)
17064                 ;;
17065                 124) error "process hangs on a deadlock"
17066                 ;;
17067                 *) error "error executing flock_deadlock $DIR/$tfile"
17068                 ;;
17069         esac
17070 }
17071 run_test 235 "LU-1715: flock deadlock detection does not work properly"
17072
17073 #LU-2935
17074 test_236() {
17075         check_swap_layouts_support
17076
17077         local ref1=/etc/passwd
17078         local ref2=/etc/group
17079         local file1=$DIR/$tdir/f1
17080         local file2=$DIR/$tdir/f2
17081
17082         test_mkdir -c1 $DIR/$tdir
17083         $LFS setstripe -c 1 $file1 || error "cannot setstripe on '$file1': rc = $?"
17084         cp $ref1 $file1 || error "cp $ref1 $file1 failed: rc = $?"
17085         $LFS setstripe -c 2 $file2 || error "cannot setstripe on '$file2': rc = $?"
17086         cp $ref2 $file2 || error "cp $ref2 $file2 failed: rc = $?"
17087         local fd=$(free_fd)
17088         local cmd="exec $fd<>$file2"
17089         eval $cmd
17090         rm $file2
17091         $LFS swap_layouts $file1 /proc/self/fd/${fd} ||
17092                 error "cannot swap layouts of '$file1' and /proc/self/fd/${fd}"
17093         cmd="exec $fd>&-"
17094         eval $cmd
17095         cmp $ref2 $file1 || error "content compare failed ($ref2 != $file1)"
17096
17097         #cleanup
17098         rm -rf $DIR/$tdir
17099 }
17100 run_test 236 "Layout swap on open unlinked file"
17101
17102 # LU-4659 linkea consistency
17103 test_238() {
17104         [[ $MDS1_VERSION -gt $(version_code 2.5.57) ]] ||
17105                 [[ $MDS1_VERSION -gt $(version_code 2.5.1) &&
17106                    $MDS1_VERSION -lt $(version_code 2.5.50) ]] ||
17107                 skip "Need MDS version at least 2.5.58 or 2.5.2+"
17108
17109         touch $DIR/$tfile
17110         ln $DIR/$tfile $DIR/$tfile.lnk
17111         touch $DIR/$tfile.new
17112         mv $DIR/$tfile.new $DIR/$tfile
17113         local fid1=$($LFS path2fid $DIR/$tfile)
17114         local fid2=$($LFS path2fid $DIR/$tfile.lnk)
17115         local path1=$($LFS fid2path $FSNAME "$fid1")
17116         [ $tfile == $path1 ] || error "linkea inconsistent: $tfile $fid1 $path1"
17117         local path2=$($LFS fid2path $FSNAME "$fid2")
17118         [ $tfile.lnk == $path2 ] ||
17119                 error "linkea inconsistent: $tfile.lnk $fid2 $path2!"
17120         rm -f $DIR/$tfile*
17121 }
17122 run_test 238 "Verify linkea consistency"
17123
17124 test_239A() { # was test_239
17125         [ $MDS1_VERSION -lt $(version_code 2.5.60) ] &&
17126                 skip "Need MDS version at least 2.5.60"
17127
17128         local list=$(comma_list $(mdts_nodes))
17129
17130         mkdir -p $DIR/$tdir
17131         createmany -o $DIR/$tdir/f- 5000
17132         unlinkmany $DIR/$tdir/f- 5000
17133         [ $MDS1_VERSION -gt $(version_code 2.10.4) ] &&
17134                 do_nodes $list "lctl set_param -n osp.*.force_sync=1"
17135         changes=$(do_nodes $list "lctl get_param -n osp.*MDT*.sync_changes \
17136                         osp.*MDT*.sync_in_flight" | calc_sum)
17137         [ "$changes" -eq 0 ] || error "$changes not synced"
17138 }
17139 run_test 239A "osp_sync test"
17140
17141 test_239a() { #LU-5297
17142         remote_mds_nodsh && skip "remote MDS with nodsh"
17143
17144         touch $DIR/$tfile
17145         #define OBD_FAIL_OSP_CHECK_INVALID_REC     0x2100
17146         do_facet $SINGLEMDS $LCTL set_param fail_loc=0x2100
17147         chgrp $RUNAS_GID $DIR/$tfile
17148         wait_delete_completed
17149 }
17150 run_test 239a "process invalid osp sync record correctly"
17151
17152 test_239b() { #LU-5297
17153         remote_mds_nodsh && skip "remote MDS with nodsh"
17154
17155         touch $DIR/$tfile1
17156         #define OBD_FAIL_OSP_CHECK_ENOMEM     0x2101
17157         do_facet $SINGLEMDS $LCTL set_param fail_loc=0x2101
17158         chgrp $RUNAS_GID $DIR/$tfile1
17159         wait_delete_completed
17160         do_facet $SINGLEMDS $LCTL set_param fail_loc=0
17161         touch $DIR/$tfile2
17162         chgrp $RUNAS_GID $DIR/$tfile2
17163         wait_delete_completed
17164 }
17165 run_test 239b "process osp sync record with ENOMEM error correctly"
17166
17167 test_240() {
17168         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
17169         remote_mds_nodsh && skip "remote MDS with nodsh"
17170
17171         mkdir -p $DIR/$tdir
17172
17173         $LFS mkdir -i 0 $DIR/$tdir/d0 ||
17174                 error "failed to mkdir $DIR/$tdir/d0 on MDT0"
17175         $LFS mkdir -i 1 $DIR/$tdir/d0/d1 ||
17176                 error "failed to mkdir $DIR/$tdir/d0/d1 on MDT1"
17177
17178         umount_client $MOUNT || error "umount failed"
17179         #define OBD_FAIL_TGT_DELAY_CONDITIONAL   0x713
17180         do_facet mds2 lctl set_param fail_loc=0x713 fail_val=1
17181         mount_client $MOUNT || error "failed to mount client"
17182
17183         echo "stat $DIR/$tdir/d0/d1, should not fail/ASSERT"
17184         stat $DIR/$tdir/d0/d1 || error "fail to stat $DIR/$tdir/d0/d1"
17185 }
17186 run_test 240 "race between ldlm enqueue and the connection RPC (no ASSERT)"
17187
17188 test_241_bio() {
17189         local count=$1
17190         local bsize=$2
17191
17192         for LOOP in $(seq $count); do
17193                 dd if=$DIR/$tfile of=/dev/null bs=$bsize count=1 2>/dev/null
17194                 cancel_lru_locks $OSC || true
17195         done
17196 }
17197
17198 test_241_dio() {
17199         local count=$1
17200         local bsize=$2
17201
17202         for LOOP in $(seq $1); do
17203                 dd if=$DIR/$tfile of=/dev/null bs=$bsize count=1 iflag=direct \
17204                         2>/dev/null
17205         done
17206 }
17207
17208 test_241a() { # was test_241
17209         local bsize=$PAGE_SIZE
17210
17211         (( bsize < 40960 )) && bsize=40960
17212         dd if=/dev/zero of=$DIR/$tfile count=1 bs=$bsize
17213         ls -la $DIR/$tfile
17214         cancel_lru_locks $OSC
17215         test_241_bio 1000 $bsize &
17216         PID=$!
17217         test_241_dio 1000 $bsize
17218         wait $PID
17219 }
17220 run_test 241a "bio vs dio"
17221
17222 test_241b() {
17223         local bsize=$PAGE_SIZE
17224
17225         (( bsize < 40960 )) && bsize=40960
17226         dd if=/dev/zero of=$DIR/$tfile count=1 bs=$bsize
17227         ls -la $DIR/$tfile
17228         test_241_dio 1000 $bsize &
17229         PID=$!
17230         test_241_dio 1000 $bsize
17231         wait $PID
17232 }
17233 run_test 241b "dio vs dio"
17234
17235 test_242() {
17236         remote_mds_nodsh && skip "remote MDS with nodsh"
17237
17238         mkdir -p $DIR/$tdir
17239         touch $DIR/$tdir/$tfile
17240
17241         #define OBD_FAIL_MDS_READPAGE_PACK      0x105
17242         do_facet mds1 lctl set_param fail_loc=0x105
17243         /bin/ls $DIR/$tdir && error "ls $DIR/$tdir should fail"
17244
17245         do_facet mds1 lctl set_param fail_loc=0
17246         /bin/ls $DIR/$tdir || error "ls $DIR/$tdir failed"
17247 }
17248 run_test 242 "mdt_readpage failure should not cause directory unreadable"
17249
17250 test_243()
17251 {
17252         test_mkdir $DIR/$tdir
17253         group_lock_test -d $DIR/$tdir || error "A group lock test failed"
17254 }
17255 run_test 243 "various group lock tests"
17256
17257 test_244a()
17258 {
17259         test_mkdir $DIR/$tdir
17260         dd if=/dev/zero of=$DIR/$tdir/$tfile bs=1M count=35
17261         sendfile_grouplock $DIR/$tdir/$tfile || \
17262                 error "sendfile+grouplock failed"
17263         rm -rf $DIR/$tdir
17264 }
17265 run_test 244a "sendfile with group lock tests"
17266
17267 test_244b()
17268 {
17269         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
17270
17271         local threads=50
17272         local size=$((1024*1024))
17273
17274         test_mkdir $DIR/$tdir
17275         for i in $(seq 1 $threads); do
17276                 local file=$DIR/$tdir/file_$((i / 10))
17277                 $MULTIOP $file OG1234w$size_$((i % 3))w$size_$((i % 4))g1234c &
17278                 local pids[$i]=$!
17279         done
17280         for i in $(seq 1 $threads); do
17281                 wait ${pids[$i]}
17282         done
17283 }
17284 run_test 244b "multi-threaded write with group lock"
17285
17286 test_245() {
17287         local flagname="multi_mod_rpcs"
17288         local connect_data_name="max_mod_rpcs"
17289         local out
17290
17291         # check if multiple modify RPCs flag is set
17292         out=$($LCTL get_param mdc.$FSNAME-MDT0000-*.import |
17293                 grep "connect_flags:")
17294         echo "$out"
17295
17296         echo "$out" | grep -qw $flagname
17297         if [ $? -ne 0 ]; then
17298                 echo "connect flag $flagname is not set"
17299                 return
17300         fi
17301
17302         # check if multiple modify RPCs data is set
17303         out=$($LCTL get_param mdc.$FSNAME-MDT0000-*.import)
17304         echo "$out"
17305
17306         echo "$out" | grep -qw $connect_data_name ||
17307                 error "import should have connect data $connect_data_name"
17308 }
17309 run_test 245 "check mdc connection flag/data: multiple modify RPCs"
17310
17311 test_246() { # LU-7371
17312         remote_ost_nodsh && skip "remote OST with nodsh"
17313         [ $OST1_VERSION -lt $(version_code 2.7.62) ] &&
17314                 skip "Need OST version >= 2.7.62"
17315
17316         do_facet ost1 $LCTL set_param fail_val=4095
17317 #define OBD_FAIL_OST_READ_SIZE          0x234
17318         do_facet ost1 $LCTL set_param fail_loc=0x234
17319         $LFS setstripe $DIR/$tfile -i 0 -c 1
17320         dd if=/dev/zero of=$DIR/$tfile bs=4095 count=1 > /dev/null 2>&1
17321         cancel_lru_locks $FSNAME-OST0000
17322         dd if=$DIR/$tfile of=/dev/null bs=1048576 || error "Read failed"
17323 }
17324 run_test 246 "Read file of size 4095 should return right length"
17325
17326 cleanup_247() {
17327         local submount=$1
17328
17329         trap 0
17330         umount_client $submount
17331         rmdir $submount
17332 }
17333
17334 test_247a() {
17335         lctl get_param -n mdc.$FSNAME-MDT0000*.import |
17336                 grep -q subtree ||
17337                 skip_env "Fileset feature is not supported"
17338
17339         local submount=${MOUNT}_$tdir
17340
17341         mkdir $MOUNT/$tdir
17342         mkdir -p $submount || error "mkdir $submount failed"
17343         FILESET="$FILESET/$tdir" mount_client $submount ||
17344                 error "mount $submount failed"
17345         trap "cleanup_247 $submount" EXIT
17346         echo foo > $submount/$tfile || error "write $submount/$tfile failed"
17347         [ $(cat $MOUNT/$tdir/$tfile) = "foo" ] ||
17348                 error "read $MOUNT/$tdir/$tfile failed"
17349         cleanup_247 $submount
17350 }
17351 run_test 247a "mount subdir as fileset"
17352
17353 test_247b() {
17354         lctl get_param -n mdc.$FSNAME-MDT0000*.import | grep -q subtree ||
17355                 skip_env "Fileset feature is not supported"
17356
17357         local submount=${MOUNT}_$tdir
17358
17359         rm -rf $MOUNT/$tdir
17360         mkdir -p $submount || error "mkdir $submount failed"
17361         SKIP_FILESET=1
17362         FILESET="$FILESET/$tdir" mount_client $submount &&
17363                 error "mount $submount should fail"
17364         rmdir $submount
17365 }
17366 run_test 247b "mount subdir that dose not exist"
17367
17368 test_247c() {
17369         lctl get_param -n mdc.$FSNAME-MDT0000*.import | grep -q subtree ||
17370                 skip_env "Fileset feature is not supported"
17371
17372         local submount=${MOUNT}_$tdir
17373
17374         mkdir -p $MOUNT/$tdir/dir1
17375         mkdir -p $submount || error "mkdir $submount failed"
17376         trap "cleanup_247 $submount" EXIT
17377         FILESET="$FILESET/$tdir" mount_client $submount ||
17378                 error "mount $submount failed"
17379         local fid=$($LFS path2fid $MOUNT/)
17380         $LFS fid2path $submount $fid && error "fid2path should fail"
17381         cleanup_247 $submount
17382 }
17383 run_test 247c "running fid2path outside root"
17384
17385 test_247d() {
17386         lctl get_param -n mdc.$FSNAME-MDT0000*.import | grep -q subtree ||
17387                 skip "Fileset feature is not supported"
17388
17389         local submount=${MOUNT}_$tdir
17390
17391         mkdir -p $MOUNT/$tdir/dir1
17392         mkdir -p $submount || error "mkdir $submount failed"
17393         FILESET="$FILESET/$tdir" mount_client $submount ||
17394                 error "mount $submount failed"
17395         trap "cleanup_247 $submount" EXIT
17396         local fid=$($LFS path2fid $submount/dir1)
17397         $LFS fid2path $submount $fid || error "fid2path should succeed"
17398         cleanup_247 $submount
17399 }
17400 run_test 247d "running fid2path inside root"
17401
17402 # LU-8037
17403 test_247e() {
17404         lctl get_param -n mdc.$FSNAME-MDT0000*.import |
17405                 grep -q subtree ||
17406                 skip "Fileset feature is not supported"
17407
17408         local submount=${MOUNT}_$tdir
17409
17410         mkdir $MOUNT/$tdir
17411         mkdir -p $submount || error "mkdir $submount failed"
17412         FILESET="$FILESET/.." mount_client $submount &&
17413                 error "mount $submount should fail"
17414         rmdir $submount
17415 }
17416 run_test 247e "mount .. as fileset"
17417
17418 test_248() {
17419         local fast_read_sav=$($LCTL get_param -n llite.*.fast_read 2>/dev/null)
17420         [ -z "$fast_read_sav" ] && skip "no fast read support"
17421
17422         # create a large file for fast read verification
17423         dd if=/dev/zero of=$DIR/$tfile bs=1M count=128 > /dev/null 2>&1
17424
17425         # make sure the file is created correctly
17426         $CHECKSTAT -s $((128*1024*1024)) $DIR/$tfile ||
17427                 { rm -f $DIR/$tfile; skip "file creation error"; }
17428
17429         echo "Test 1: verify that fast read is 4 times faster on cache read"
17430
17431         # small read with fast read enabled
17432         $LCTL set_param -n llite.*.fast_read=1
17433         local t_fast=$(dd if=$DIR/$tfile of=/dev/null bs=4k 2>&1 |
17434                 egrep -o '([[:digit:]\.\,e-]+) s' | cut -d's' -f1 |
17435                 sed -e 's/,/./' -e 's/[eE]+*/\*10\^/')
17436         # small read with fast read disabled
17437         $LCTL set_param -n llite.*.fast_read=0
17438         local t_slow=$(dd if=$DIR/$tfile of=/dev/null bs=4k 2>&1 |
17439                 egrep -o '([[:digit:]\.\,e-]+) s' | cut -d's' -f1 |
17440                 sed -e 's/,/./' -e 's/[eE]+*/\*10\^/')
17441
17442         # verify that fast read is 4 times faster for cache read
17443         [ $(bc <<< "4 * $t_fast < $t_slow") -eq 1 ] ||
17444                 error_not_in_vm "fast read was not 4 times faster: " \
17445                            "$t_fast vs $t_slow"
17446
17447         echo "Test 2: verify the performance between big and small read"
17448         $LCTL set_param -n llite.*.fast_read=1
17449
17450         # 1k non-cache read
17451         cancel_lru_locks osc
17452         local t_1k=$(dd if=$DIR/$tfile of=/dev/null bs=1k 2>&1 |
17453                 egrep -o '([[:digit:]\.\,e-]+) s' | cut -d's' -f1 |
17454                 sed -e 's/,/./' -e 's/[eE]+*/\*10\^/')
17455
17456         # 1M non-cache read
17457         cancel_lru_locks osc
17458         local t_1m=$(dd if=$DIR/$tfile of=/dev/null bs=1k 2>&1 |
17459                 egrep -o '([[:digit:]\.\,e-]+) s' | cut -d's' -f1 |
17460                 sed -e 's/,/./' -e 's/[eE]+*/\*10\^/')
17461
17462         # verify that big IO is not 4 times faster than small IO
17463         [ $(bc <<< "4 * $t_1k >= $t_1m") -eq 1 ] ||
17464                 error_not_in_vm "bigger IO is way too fast: $t_1k vs $t_1m"
17465
17466         $LCTL set_param -n llite.*.fast_read=$fast_read_sav
17467         rm -f $DIR/$tfile
17468 }
17469 run_test 248 "fast read verification"
17470
17471 test_249() { # LU-7890
17472         [ $MDS1_VERSION -lt $(version_code 2.8.53) ] &&
17473                 skip "Need at least version 2.8.54"
17474
17475         rm -f $DIR/$tfile
17476         $LFS setstripe -c 1 $DIR/$tfile
17477         # Offset 2T == 4k * 512M
17478         dd if=/dev/zero of=$DIR/$tfile bs=4k count=1 seek=512M ||
17479                 error "dd to 2T offset failed"
17480 }
17481 run_test 249 "Write above 2T file size"
17482
17483 test_250() {
17484         [ "$(facet_fstype ost$(($($LFS getstripe -i $DIR/$tfile) + 1)))" = "zfs" ] \
17485          && skip "no 16TB file size limit on ZFS"
17486
17487         $LFS setstripe -c 1 $DIR/$tfile
17488         # ldiskfs extent file size limit is (16TB - 4KB - 1) bytes
17489         local size=$((16 * 1024 * 1024 * 1024 * 1024 - 4096 - 1))
17490         $TRUNCATE $DIR/$tfile $size || error "truncate $tfile to $size failed"
17491         dd if=/dev/zero of=$DIR/$tfile bs=10 count=1 oflag=append \
17492                 conv=notrunc,fsync && error "append succeeded"
17493         return 0
17494 }
17495 run_test 250 "Write above 16T limit"
17496
17497 test_251() {
17498         $LFS setstripe -c -1 -S 1048576 $DIR/$tfile
17499
17500         #define OBD_FAIL_LLITE_LOST_LAYOUT 0x1407
17501         #Skip once - writing the first stripe will succeed
17502         $LCTL set_param fail_loc=0xa0001407 fail_val=1
17503         $MULTIOP $DIR/$tfile o:O_RDWR:w2097152c 2>&1 | grep -q "short write" &&
17504                 error "short write happened"
17505
17506         $LCTL set_param fail_loc=0xa0001407 fail_val=1
17507         $MULTIOP $DIR/$tfile or2097152c 2>&1 | grep -q "short read" &&
17508                 error "short read happened"
17509
17510         rm -f $DIR/$tfile
17511 }
17512 run_test 251 "Handling short read and write correctly"
17513
17514 test_252() {
17515         remote_mds_nodsh && skip "remote MDS with nodsh"
17516         remote_ost_nodsh && skip "remote OST with nodsh"
17517         if [ "$ost1_FSTYPE" != ldiskfs ] || [ "$mds1_FSTYPE" != ldiskfs ]; then
17518                 skip_env "ldiskfs only test"
17519         fi
17520
17521         local tgt
17522         local dev
17523         local out
17524         local uuid
17525         local num
17526         local gen
17527
17528         # check lr_reader on OST0000
17529         tgt=ost1
17530         dev=$(facet_device $tgt)
17531         out=$(do_facet $tgt $LR_READER $dev)
17532         [ $? -eq 0 ] || error "$LR_READER failed on target $tgt device $dev"
17533         echo "$out"
17534         uuid=$(echo "$out" | grep -i uuid | awk '{ print $2 }')
17535         [ "$uuid" == "$(ostuuid_from_index 0)" ] ||
17536                 error "Invalid uuid returned by $LR_READER on target $tgt"
17537         echo -e "uuid returned by $LR_READER is '$uuid'\n"
17538
17539         # check lr_reader -c on MDT0000
17540         tgt=mds1
17541         dev=$(facet_device $tgt)
17542         if ! do_facet $tgt $LR_READER -h | grep -q OPTIONS; then
17543                 skip "$LR_READER does not support additional options"
17544         fi
17545         out=$(do_facet $tgt $LR_READER -c $dev)
17546         [ $? -eq 0 ] || error "$LR_READER failed on target $tgt device $dev"
17547         echo "$out"
17548         num=$(echo "$out" | grep -c "mdtlov")
17549         [ "$num" -eq $((MDSCOUNT - 1)) ] ||
17550                 error "Invalid number of mdtlov clients returned by $LR_READER"
17551         echo -e "Number of mdtlov clients returned by $LR_READER is '$num'\n"
17552
17553         # check lr_reader -cr on MDT0000
17554         out=$(do_facet $tgt $LR_READER -cr $dev)
17555         [ $? -eq 0 ] || error "$LR_READER failed on target $tgt device $dev"
17556         echo "$out"
17557         echo "$out" | grep -q "^reply_data:$" ||
17558                 error "$LR_READER should have returned 'reply_data' section"
17559         num=$(echo "$out" | grep -c "client_generation")
17560         echo -e "Number of reply data returned by $LR_READER is '$num'\n"
17561 }
17562 run_test 252 "check lr_reader tool"
17563
17564 test_253() {
17565         [ $PARALLEL == "yes" ] && skip "skip parallel run"
17566         remote_mds_nodsh && skip "remote MDS with nodsh"
17567         remote_mgs_nodsh && skip "remote MGS with nodsh"
17568
17569         local ostidx=0
17570         local rc=0
17571         local ost_name=$(ostname_from_index $ostidx)
17572
17573         # on the mdt's osc
17574         local mdtosc_proc1=$(get_mdtosc_proc_path $SINGLEMDS $ost_name)
17575         do_facet $SINGLEMDS $LCTL get_param -n \
17576                 osp.$mdtosc_proc1.reserved_mb_high ||
17577                 skip  "remote MDS does not support reserved_mb_high"
17578
17579         rm -rf $DIR/$tdir
17580         wait_mds_ost_sync
17581         wait_delete_completed
17582         mkdir $DIR/$tdir
17583
17584         pool_add $TESTNAME || error "Pool creation failed"
17585         pool_add_targets $TESTNAME 0 || error "Pool add targets failed"
17586
17587         $LFS setstripe $DIR/$tdir -i $ostidx -c 1 -p $FSNAME.$TESTNAME ||
17588                 error "Setstripe failed"
17589
17590         dd if=/dev/zero of=$DIR/$tdir/$tfile.0 bs=1M count=10
17591
17592         local wms=$(ost_watermarks_set_enospc $tfile $ostidx |
17593                     grep "watermarks")
17594         stack_trap "ost_watermarks_clear_enospc $tfile $ostidx $wms" EXIT
17595
17596         local oa_status=$(do_facet $SINGLEMDS $LCTL get_param -n \
17597                         osp.$mdtosc_proc1.prealloc_status)
17598         echo "prealloc_status $oa_status"
17599
17600         dd if=/dev/zero of=$DIR/$tdir/$tfile.1 bs=1M count=1 &&
17601                 error "File creation should fail"
17602
17603         #object allocation was stopped, but we still able to append files
17604         dd if=/dev/zero of=$DIR/$tdir/$tfile.0 bs=1M seek=6 count=5 \
17605                 oflag=append || error "Append failed"
17606
17607         rm -f $DIR/$tdir/$tfile.0
17608
17609         # For this test, we want to delete the files we created to go out of
17610         # space but leave the watermark, so we remain nearly out of space
17611         ost_watermarks_enospc_delete_files $tfile $ostidx
17612
17613         wait_delete_completed
17614
17615         sleep_maxage
17616
17617         for i in $(seq 10 12); do
17618                 dd if=/dev/zero of=$DIR/$tdir/$tfile.$i bs=1M count=1 \
17619                         2>/dev/null || error "File creation failed after rm"
17620         done
17621
17622         oa_status=$(do_facet $SINGLEMDS $LCTL get_param -n \
17623                         osp.$mdtosc_proc1.prealloc_status)
17624         echo "prealloc_status $oa_status"
17625
17626         if (( oa_status != 0 )); then
17627                 error "Object allocation still disable after rm"
17628         fi
17629 }
17630 run_test 253 "Check object allocation limit"
17631
17632 test_254() {
17633         [ $PARALLEL == "yes" ] && skip "skip parallel run"
17634         remote_mds_nodsh && skip "remote MDS with nodsh"
17635         do_facet $SINGLEMDS $LCTL get_param -n mdd.$MDT0.changelog_size ||
17636                 skip "MDS does not support changelog_size"
17637
17638         local cl_user
17639         local MDT0=$(facet_svc $SINGLEMDS)
17640
17641         changelog_register || error "changelog_register failed"
17642
17643         changelog_clear 0 || error "changelog_clear failed"
17644
17645         local size1=$(do_facet $SINGLEMDS \
17646                       $LCTL get_param -n mdd.$MDT0.changelog_size)
17647         echo "Changelog size $size1"
17648
17649         rm -rf $DIR/$tdir
17650         $LFS mkdir -i 0 $DIR/$tdir
17651         # change something
17652         mkdir -p $DIR/$tdir/pics/2008/zachy
17653         touch $DIR/$tdir/pics/2008/zachy/timestamp
17654         cp /etc/hosts $DIR/$tdir/pics/2008/zachy/pic1.jpg
17655         mv $DIR/$tdir/pics/2008/zachy $DIR/$tdir/pics/zach
17656         ln $DIR/$tdir/pics/zach/pic1.jpg $DIR/$tdir/pics/2008/portland.jpg
17657         ln -s $DIR/$tdir/pics/2008/portland.jpg $DIR/$tdir/pics/desktop.jpg
17658         rm $DIR/$tdir/pics/desktop.jpg
17659
17660         local size2=$(do_facet $SINGLEMDS \
17661                       $LCTL get_param -n mdd.$MDT0.changelog_size)
17662         echo "Changelog size after work $size2"
17663
17664         (( $size2 > $size1 )) ||
17665                 error "new Changelog size=$size2 less than old size=$size1"
17666 }
17667 run_test 254 "Check changelog size"
17668
17669 ladvise_no_type()
17670 {
17671         local type=$1
17672         local file=$2
17673
17674         lfs ladvise -a invalid $file 2>&1 | grep "Valid types" |
17675                 awk -F: '{print $2}' | grep $type > /dev/null
17676         if [ $? -ne 0 ]; then
17677                 return 0
17678         fi
17679         return 1
17680 }
17681
17682 ladvise_no_ioctl()
17683 {
17684         local file=$1
17685
17686         lfs ladvise -a willread $file > /dev/null 2>&1
17687         if [ $? -eq 0 ]; then
17688                 return 1
17689         fi
17690
17691         lfs ladvise -a willread $file 2>&1 |
17692                 grep "Inappropriate ioctl for device" > /dev/null
17693         if [ $? -eq 0 ]; then
17694                 return 0
17695         fi
17696         return 1
17697 }
17698
17699 percent() {
17700         bc <<<"scale=2; ($1 - $2) * 100 / $2"
17701 }
17702
17703 # run a random read IO workload
17704 # usage: random_read_iops <filename> <filesize> <iosize>
17705 random_read_iops() {
17706         local file=$1
17707         local fsize=$2
17708         local iosize=${3:-4096}
17709
17710         $READS -f $file -s $fsize -b $iosize -n $((fsize / iosize)) -t 60 |
17711                 sed -e '/^$/d' -e 's#.*s, ##' -e 's#MB/s##'
17712 }
17713
17714 drop_file_oss_cache() {
17715         local file="$1"
17716         local nodes="$2"
17717
17718         $LFS ladvise -a dontneed $file 2>/dev/null ||
17719                 do_nodes $nodes "echo 3 > /proc/sys/vm/drop_caches"
17720 }
17721
17722 ladvise_willread_performance()
17723 {
17724         local repeat=10
17725         local average_origin=0
17726         local average_cache=0
17727         local average_ladvise=0
17728
17729         for ((i = 1; i <= $repeat; i++)); do
17730                 echo "Iter $i/$repeat: reading without willread hint"
17731                 cancel_lru_locks osc
17732                 drop_file_oss_cache $DIR/$tfile $(comma_list $(osts_nodes))
17733                 local speed_origin=$(random_read_iops $DIR/$tfile $size)
17734                 echo "Iter $i/$repeat: uncached speed: $speed_origin"
17735                 average_origin=$(bc <<<"$average_origin + $speed_origin")
17736
17737                 cancel_lru_locks osc
17738                 local speed_cache=$(random_read_iops $DIR/$tfile $size)
17739                 echo "Iter $i/$repeat: OSS cache speed: $speed_cache"
17740                 average_cache=$(bc <<<"$average_cache + $speed_cache")
17741
17742                 cancel_lru_locks osc
17743                 drop_file_oss_cache $DIR/$tfile $(comma_list $(osts_nodes))
17744                 $LFS ladvise -a willread $DIR/$tfile || error "ladvise failed"
17745                 local speed_ladvise=$(random_read_iops $DIR/$tfile $size)
17746                 echo "Iter $i/$repeat: ladvise speed: $speed_ladvise"
17747                 average_ladvise=$(bc <<<"$average_ladvise + $speed_ladvise")
17748         done
17749         average_origin=$(bc <<<"scale=2; $average_origin / $repeat")
17750         average_cache=$(bc <<<"scale=2; $average_cache / $repeat")
17751         average_ladvise=$(bc <<<"scale=2; $average_ladvise / $repeat")
17752
17753         speedup_cache=$(percent $average_cache $average_origin)
17754         speedup_ladvise=$(percent $average_ladvise $average_origin)
17755
17756         echo "Average uncached read: $average_origin"
17757         echo "Average speedup with OSS cached read: " \
17758                 "$average_cache = +$speedup_cache%"
17759         echo "Average speedup with ladvise willread: " \
17760                 "$average_ladvise = +$speedup_ladvise%"
17761
17762         local lowest_speedup=20
17763         if [ ${average_cache%.*} -lt $lowest_speedup ]; then
17764                 echo "Speedup with OSS cached read less than $lowest_speedup%," \
17765                         "got $average_cache%. Skipping ladvise willread check."
17766                 return 0
17767         fi
17768
17769         # the test won't work on ZFS until it supports 'ladvise dontneed', but
17770         # it is still good to run until then to exercise 'ladvise willread'
17771         ! $LFS ladvise -a dontneed $DIR/$tfile &&
17772                 [ "$ost1_FSTYPE" = "zfs" ] &&
17773                 echo "osd-zfs does not support dontneed or drop_caches" &&
17774                 return 0
17775
17776         lowest_speedup=$(bc <<<"scale=2; $average_cache / 2")
17777         [ ${average_ladvise%.*} -gt $lowest_speedup ] ||
17778                 error_not_in_vm "Speedup with willread is less than " \
17779                         "$lowest_speedup%, got $average_ladvise%"
17780 }
17781
17782 test_255a() {
17783         [ $OST1_VERSION -lt $(version_code 2.8.54) ] &&
17784                 skip "lustre < 2.8.54 does not support ladvise "
17785         remote_ost_nodsh && skip "remote OST with nodsh"
17786
17787         lfs setstripe -c -1 -i 0 $DIR/$tfile || error "$tfile failed"
17788
17789         ladvise_no_type willread $DIR/$tfile &&
17790                 skip "willread ladvise is not supported"
17791
17792         ladvise_no_ioctl $DIR/$tfile &&
17793                 skip "ladvise ioctl is not supported"
17794
17795         local size_mb=100
17796         local size=$((size_mb * 1048576))
17797         dd if=/dev/zero of=$DIR/$tfile bs=1048576 count=$size_mb ||
17798                 error "dd to $DIR/$tfile failed"
17799
17800         lfs ladvise -a willread $DIR/$tfile ||
17801                 error "Ladvise failed with no range argument"
17802
17803         lfs ladvise -a willread -s 0 $DIR/$tfile ||
17804                 error "Ladvise failed with no -l or -e argument"
17805
17806         lfs ladvise -a willread -e 1 $DIR/$tfile ||
17807                 error "Ladvise failed with only -e argument"
17808
17809         lfs ladvise -a willread -l 1 $DIR/$tfile ||
17810                 error "Ladvise failed with only -l argument"
17811
17812         lfs ladvise -a willread -s 2 -e 1 $DIR/$tfile &&
17813                 error "End offset should not be smaller than start offset"
17814
17815         lfs ladvise -a willread -s 2 -e 2 $DIR/$tfile &&
17816                 error "End offset should not be equal to start offset"
17817
17818         lfs ladvise -a willread -s $size -l 1 $DIR/$tfile ||
17819                 error "Ladvise failed with overflowing -s argument"
17820
17821         lfs ladvise -a willread -s 1 -e $((size + 1)) $DIR/$tfile ||
17822                 error "Ladvise failed with overflowing -e argument"
17823
17824         lfs ladvise -a willread -s 1 -l $size $DIR/$tfile ||
17825                 error "Ladvise failed with overflowing -l argument"
17826
17827         lfs ladvise -a willread -l 1 -e 2 $DIR/$tfile &&
17828                 error "Ladvise succeeded with conflicting -l and -e arguments"
17829
17830         echo "Synchronous ladvise should wait"
17831         local delay=4
17832 #define OBD_FAIL_OST_LADVISE_PAUSE       0x237
17833         do_nodes $(comma_list $(osts_nodes)) \
17834                 $LCTL set_param fail_val=$delay fail_loc=0x237
17835
17836         local start_ts=$SECONDS
17837         lfs ladvise -a willread $DIR/$tfile ||
17838                 error "Ladvise failed with no range argument"
17839         local end_ts=$SECONDS
17840         local inteval_ts=$((end_ts - start_ts))
17841
17842         if [ $inteval_ts -lt $(($delay - 1)) ]; then
17843                 error "Synchronous advice didn't wait reply"
17844         fi
17845
17846         echo "Asynchronous ladvise shouldn't wait"
17847         local start_ts=$SECONDS
17848         lfs ladvise -a willread -b $DIR/$tfile ||
17849                 error "Ladvise failed with no range argument"
17850         local end_ts=$SECONDS
17851         local inteval_ts=$((end_ts - start_ts))
17852
17853         if [ $inteval_ts -gt $(($delay / 2)) ]; then
17854                 error "Asynchronous advice blocked"
17855         fi
17856
17857         do_nodes $(comma_list $(osts_nodes)) $LCTL set_param fail_loc=0
17858         ladvise_willread_performance
17859 }
17860 run_test 255a "check 'lfs ladvise -a willread'"
17861
17862 facet_meminfo() {
17863         local facet=$1
17864         local info=$2
17865
17866         do_facet $facet "cat /proc/meminfo | grep ^${info}:" | awk '{print $2}'
17867 }
17868
17869 test_255b() {
17870         [ $OST1_VERSION -lt $(version_code 2.8.54) ] &&
17871                 skip "lustre < 2.8.54 does not support ladvise "
17872         remote_ost_nodsh && skip "remote OST with nodsh"
17873
17874         lfs setstripe -c 1 -i 0 $DIR/$tfile
17875
17876         ladvise_no_type dontneed $DIR/$tfile &&
17877                 skip "dontneed ladvise is not supported"
17878
17879         ladvise_no_ioctl $DIR/$tfile &&
17880                 skip "ladvise ioctl is not supported"
17881
17882         ! $LFS ladvise -a dontneed $DIR/$tfile &&
17883                 [ "$ost1_FSTYPE" = "zfs" ] &&
17884                 skip "zfs-osd does not support 'ladvise dontneed'"
17885
17886         local size_mb=100
17887         local size=$((size_mb * 1048576))
17888         # In order to prevent disturbance of other processes, only check 3/4
17889         # of the memory usage
17890         local kibibytes=$((size_mb * 1024 * 3 / 4))
17891
17892         dd if=/dev/zero of=$DIR/$tfile bs=1048576 count=$size_mb ||
17893                 error "dd to $DIR/$tfile failed"
17894
17895         #force write to complete before dropping OST cache & checking memory
17896         sync
17897
17898         local total=$(facet_meminfo ost1 MemTotal)
17899         echo "Total memory: $total KiB"
17900
17901         do_facet ost1 "sync && echo 3 > /proc/sys/vm/drop_caches"
17902         local before_read=$(facet_meminfo ost1 Cached)
17903         echo "Cache used before read: $before_read KiB"
17904
17905         lfs ladvise -a willread $DIR/$tfile ||
17906                 error "Ladvise willread failed"
17907         local after_read=$(facet_meminfo ost1 Cached)
17908         echo "Cache used after read: $after_read KiB"
17909
17910         lfs ladvise -a dontneed $DIR/$tfile ||
17911                 error "Ladvise dontneed again failed"
17912         local no_read=$(facet_meminfo ost1 Cached)
17913         echo "Cache used after dontneed ladvise: $no_read KiB"
17914
17915         if [ $total -lt $((before_read + kibibytes)) ]; then
17916                 echo "Memory is too small, abort checking"
17917                 return 0
17918         fi
17919
17920         if [ $((before_read + kibibytes)) -gt $after_read ]; then
17921                 error "Ladvise willread should use more memory" \
17922                         "than $kibibytes KiB"
17923         fi
17924
17925         if [ $((no_read + kibibytes)) -gt $after_read ]; then
17926                 error "Ladvise dontneed should release more memory" \
17927                         "than $kibibytes KiB"
17928         fi
17929 }
17930 run_test 255b "check 'lfs ladvise -a dontneed'"
17931
17932 test_255c() {
17933         [ $OST1_VERSION -lt $(version_code 2.10.50) ] &&
17934                 skip "lustre < 2.10.50 does not support lockahead"
17935
17936         local count
17937         local new_count
17938         local difference
17939         local i
17940         local rc
17941
17942         test_mkdir -p $DIR/$tdir
17943         $LFS setstripe -i 0 -c 1 $DIR/$tdir
17944
17945         #test 10 returns only success/failure
17946         i=10
17947         lockahead_test -d $DIR/$tdir -t $i -f $tfile
17948         rc=$?
17949         if [ $rc -eq 255 ]; then
17950                 error "Ladvise test${i} failed, ${rc}"
17951         fi
17952
17953         #test 11 counts lock enqueue requests, all others count new locks
17954         i=11
17955         count=$(do_facet ost1 \
17956                 $LCTL get_param -n ost.OSS.ost.stats)
17957         count=$(echo "$count" | grep ldlm_extent_enqueue | awk '{ print $2 }')
17958
17959         lockahead_test -d $DIR/$tdir -t $i -f $tfile
17960         rc=$?
17961         if [ $rc -eq 255 ]; then
17962                 error "Ladvise test${i} failed, ${rc}"
17963         fi
17964
17965         new_count=$(do_facet ost1 \
17966                 $LCTL get_param -n ost.OSS.ost.stats)
17967         new_count=$(echo "$new_count" | grep ldlm_extent_enqueue | \
17968                    awk '{ print $2 }')
17969
17970         difference="$((new_count - count))"
17971         if [ $difference -ne $rc ]; then
17972                 error "Ladvise test${i}, bad enqueue count, returned " \
17973                       "${rc}, actual ${difference}"
17974         fi
17975
17976         for i in $(seq 12 21); do
17977                 # If we do not do this, we run the risk of having too many
17978                 # locks and starting lock cancellation while we are checking
17979                 # lock counts.
17980                 cancel_lru_locks osc
17981
17982                 count=$($LCTL get_param -n \
17983                        ldlm.namespaces.$FSNAME-OST0000*osc-[-0-9a-f]*.lock_unused_count)
17984
17985                 lockahead_test -d $DIR/$tdir -t $i -f $tfile
17986                 rc=$?
17987                 if [ $rc -eq 255 ]; then
17988                         error "Ladvise test ${i} failed, ${rc}"
17989                 fi
17990
17991                 new_count=$($LCTL get_param -n \
17992                        ldlm.namespaces.$FSNAME-OST0000*osc-[-0-9a-f]*.lock_unused_count)
17993                 difference="$((new_count - count))"
17994
17995                 # Test 15 output is divided by 100 to map down to valid return
17996                 if [ $i -eq 15 ]; then
17997                         rc="$((rc * 100))"
17998                 fi
17999
18000                 if [ $difference -ne $rc ]; then
18001                         error "Ladvise test ${i}, bad lock count, returned " \
18002                               "${rc}, actual ${difference}"
18003                 fi
18004         done
18005
18006         #test 22 returns only success/failure
18007         i=22
18008         lockahead_test -d $DIR/$tdir -t $i -f $tfile
18009         rc=$?
18010         if [ $rc -eq 255 ]; then
18011                 error "Ladvise test${i} failed, ${rc}"
18012         fi
18013 }
18014 run_test 255c "suite of ladvise lockahead tests"
18015
18016 test_256() {
18017         [ $PARALLEL == "yes" ] && skip "skip parallel run"
18018         remote_mds_nodsh && skip "remote MDS with nodsh"
18019         [ "$mds1_FSTYPE" != "ldiskfs" ] && skip "ldiskfs only test"
18020         changelog_users $SINGLEMDS | grep "^cl" &&
18021                 skip "active changelog user"
18022
18023         local cl_user
18024         local cat_sl
18025         local mdt_dev
18026
18027         mdt_dev=$(mdsdevname 1)
18028         echo $mdt_dev
18029
18030         changelog_register || error "changelog_register failed"
18031
18032         rm -rf $DIR/$tdir
18033         mkdir -p $DIR/$tdir
18034
18035         changelog_clear 0 || error "changelog_clear failed"
18036
18037         # change something
18038         touch $DIR/$tdir/{1..10}
18039
18040         # stop the MDT
18041         stop $SINGLEMDS || error "Fail to stop MDT"
18042
18043         # remount the MDT
18044
18045         start $SINGLEMDS $mdt_dev $MDS_MOUNT_OPTS || error "Fail to start MDT"
18046
18047         #after mount new plainllog is used
18048         touch $DIR/$tdir/{11..19}
18049         local tmpfile="$(mktemp --tmpdir -u $tfile.XXXXXX)"
18050         stack_trap "rm -f $tmpfile"
18051         cat_sl=$(do_facet $SINGLEMDS "sync; \
18052                  $DEBUGFS -c -R 'dump changelog_catalog $tmpfile' $mdt_dev; \
18053                  llog_reader $tmpfile | grep -c type=1064553b")
18054         do_facet $SINGLEMDS llog_reader $tmpfile
18055
18056         [ $cat_sl != 2 ] && error "Changelog catalog has $cat_sl != 2 slots"
18057
18058         changelog_clear 0 || error "changelog_clear failed"
18059
18060         cat_sl=$(do_facet $SINGLEMDS "sync; \
18061                  $DEBUGFS -c -R 'dump changelog_catalog $tmpfile' $mdt_dev; \
18062                  llog_reader $tmpfile | grep -c type=1064553b")
18063
18064         if (( cat_sl == 2 )); then
18065                 error "Empty plain llog was not deleted from changelog catalog"
18066         elif (( cat_sl != 1 )); then
18067                 error "Active plain llog shouldn't be deleted from catalog"
18068         fi
18069 }
18070 run_test 256 "Check llog delete for empty and not full state"
18071
18072 test_257() {
18073         remote_mds_nodsh && skip "remote MDS with nodsh"
18074         [[ $MDS1_VERSION -lt $(version_code 2.8.55) ]] &&
18075                 skip "Need MDS version at least 2.8.55"
18076
18077         test_mkdir $DIR/$tdir
18078
18079         setfattr -n trusted.name1 -v value1 $DIR/$tdir ||
18080                 error "setfattr -n trusted.name1=value1 $DIR/$tdir failed"
18081         stat $DIR/$tdir
18082
18083 #define OBD_FAIL_MDS_XATTR_REP                  0x161
18084         local mdtidx=$($LFS getstripe -m $DIR/$tdir)
18085         local facet=mds$((mdtidx + 1))
18086         set_nodes_failloc $(facet_active_host $facet) 0x80000161
18087         getfattr -n trusted.name1 $DIR/$tdir 2> /dev/null
18088
18089         stop $facet || error "stop MDS failed"
18090         start $facet $(mdsdevname $((mdtidx + 1))) $MDS_MOUNT_OPTS ||
18091                 error "start MDS fail"
18092         wait_recovery_complete $facet
18093 }
18094 run_test 257 "xattr locks are not lost"
18095
18096 # Verify we take the i_mutex when security requires it
18097 test_258a() {
18098 #define OBD_FAIL_IMUTEX_SEC 0x141c
18099         $LCTL set_param fail_loc=0x141c
18100         touch $DIR/$tfile
18101         chmod u+s $DIR/$tfile
18102         chmod a+rwx $DIR/$tfile
18103         $RUNAS dd if=/dev/zero of=$DIR/$tfile bs=4k count=1 oflag=append
18104         RC=$?
18105         if [ $RC -ne 0 ]; then
18106                 error "error, failed to take i_mutex, rc=$?"
18107         fi
18108         rm -f $DIR/$tfile
18109 }
18110 run_test 258a "verify i_mutex security behavior when suid attributes is set"
18111
18112 # Verify we do NOT take the i_mutex in the normal case
18113 test_258b() {
18114 #define OBD_FAIL_IMUTEX_NOSEC 0x141d
18115         $LCTL set_param fail_loc=0x141d
18116         touch $DIR/$tfile
18117         chmod a+rwx $DIR
18118         chmod a+rw $DIR/$tfile
18119         $RUNAS dd if=/dev/zero of=$DIR/$tfile bs=4k count=1 oflag=append
18120         RC=$?
18121         if [ $RC -ne 0 ]; then
18122                 error "error, took i_mutex unnecessarily, rc=$?"
18123         fi
18124         rm -f $DIR/$tfile
18125
18126 }
18127 run_test 258b "verify i_mutex security behavior"
18128
18129 test_259() {
18130         local file=$DIR/$tfile
18131         local before
18132         local after
18133
18134         [ "$mds1_FSTYPE" != "ldiskfs" ] && skip "ldiskfs only test"
18135
18136         stack_trap "rm -f $file" EXIT
18137
18138         wait_delete_completed
18139         before=$(do_facet ost1 "$LCTL get_param -n osd-*.*OST0000.kbytesfree")
18140         echo "before: $before"
18141
18142         $LFS setstripe -i 0 -c 1 $file
18143         dd if=/dev/zero of=$file bs=1M count=10 || error "couldn't write"
18144         sync_all_data
18145         after=$(do_facet ost1 "$LCTL get_param -n osd-*.*OST0000.kbytesfree")
18146         echo "after write: $after"
18147
18148 #define OBD_FAIL_OSD_FAIL_AT_TRUNCATE          0x2301
18149         do_facet ost1 $LCTL set_param fail_loc=0x2301
18150         $TRUNCATE $file 0
18151         after=$(do_facet ost1 "$LCTL get_param -n osd-*.*OST0000.kbytesfree")
18152         echo "after truncate: $after"
18153
18154         stop ost1
18155         do_facet ost1 $LCTL set_param fail_loc=0
18156         start ost1 $(ostdevname 1) $OST_MOUNT_OPTS || error "cannot start ost1"
18157         sleep 2
18158         after=$(do_facet ost1 "$LCTL get_param -n osd-*.*OST0000.kbytesfree")
18159         echo "after restart: $after"
18160         [ $((after - before)) -ge $(fs_log_size ost1) ] &&
18161                 error "missing truncate?"
18162
18163         return 0
18164 }
18165 run_test 259 "crash at delayed truncate"
18166
18167 test_260() {
18168 #define OBD_FAIL_MDC_CLOSE               0x806
18169         $LCTL set_param fail_loc=0x80000806
18170         touch $DIR/$tfile
18171
18172 }
18173 run_test 260 "Check mdc_close fail"
18174
18175 ### Data-on-MDT sanity tests ###
18176 test_270a() {
18177         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
18178                 skip "Need MDS version at least 2.10.55 for DoM"
18179
18180         # create DoM file
18181         local dom=$DIR/$tdir/dom_file
18182         local tmp=$DIR/$tdir/tmp_file
18183
18184         mkdir -p $DIR/$tdir
18185
18186         # basic checks for DoM component creation
18187         $LFS setstripe -E 1024K -E 2048K -L mdt $dom 2>/dev/null &&
18188                 error "Can set MDT layout to non-first entry"
18189
18190         $LFS setstripe -E 1024K -L mdt -E 2048K -L mdt $dom 2>/dev/null &&
18191                 error "Can define multiple entries as MDT layout"
18192
18193         $LFS setstripe -E 1M -L mdt $dom || error "Can't create DoM layout"
18194
18195         [ $($LFS getstripe -L $dom) == "mdt" ] || error "bad pattern"
18196         [ $($LFS getstripe -c $dom) == 0 ] || error "bad stripe count"
18197         [ $($LFS getstripe -S $dom) == 1048576 ] || error "bad stripe size"
18198
18199         local mdtidx=$($LFS getstripe -m $dom)
18200         local mdtname=MDT$(printf %04x $mdtidx)
18201         local facet=mds$((mdtidx + 1))
18202         local space_check=1
18203
18204         # Skip free space checks with ZFS
18205         [ "$(facet_fstype $facet)" == "zfs" ] && space_check=0
18206
18207         # write
18208         sync
18209         local size_tmp=$((65536 * 3))
18210         local mdtfree1=$(do_facet $facet \
18211                          lctl get_param -n osd*.*$mdtname.kbytesfree)
18212
18213         dd if=/dev/urandom of=$tmp bs=1024 count=$((size_tmp / 1024))
18214         # check also direct IO along write
18215         # IO size must be a multiple of PAGE_SIZE on all platforms (ARM=64KB)
18216         dd if=$tmp of=$dom bs=65536 count=$((size_tmp / 65536)) oflag=direct
18217         sync
18218         cmp $tmp $dom || error "file data is different"
18219         [ $(stat -c%s $dom) == $size_tmp ] ||
18220                 error "bad size after write: $(stat -c%s $dom) != $size_tmp"
18221         if [ $space_check == 1 ]; then
18222                 local mdtfree2=$(do_facet $facet \
18223                                  lctl get_param -n osd*.*$mdtname.kbytesfree)
18224
18225                 # increase in usage from by $size_tmp
18226                 [ $(($mdtfree1 - $mdtfree2)) -ge $((size_tmp / 1024)) ] ||
18227                         error "MDT free space wrong after write: " \
18228                               "$mdtfree1 >= $mdtfree2 + $size_tmp/1024"
18229         fi
18230
18231         # truncate
18232         local size_dom=10000
18233
18234         $TRUNCATE $dom $size_dom
18235         [ $(stat -c%s $dom) == $size_dom ] ||
18236                 error "bad size after truncate: $(stat -c%s $dom) != $size_dom"
18237         if [ $space_check == 1 ]; then
18238                 mdtfree1=$(do_facet $facet \
18239                                 lctl get_param -n osd*.*$mdtname.kbytesfree)
18240                 # decrease in usage from $size_tmp to new $size_dom
18241                 [ $(($mdtfree1 - $mdtfree2)) -ge \
18242                   $(((size_tmp - size_dom) / 1024)) ] ||
18243                         error "MDT free space is wrong after truncate: " \
18244                               "$mdtfree1 >= $mdtfree2 + ($size_tmp - $size_dom) / 1024"
18245         fi
18246
18247         # append
18248         cat $tmp >> $dom
18249         sync
18250         size_dom=$((size_dom + size_tmp))
18251         [ $(stat -c%s $dom) == $size_dom ] ||
18252                 error "bad size after append: $(stat -c%s $dom) != $size_dom"
18253         if [ $space_check == 1 ]; then
18254                 mdtfree2=$(do_facet $facet \
18255                                 lctl get_param -n osd*.*$mdtname.kbytesfree)
18256                 # increase in usage by $size_tmp from previous
18257                 [ $(($mdtfree1 - $mdtfree2)) -ge $((size_tmp / 1024)) ] ||
18258                         error "MDT free space is wrong after append: " \
18259                               "$mdtfree1 >= $mdtfree2 + $size_tmp/1024"
18260         fi
18261
18262         # delete
18263         rm $dom
18264         if [ $space_check == 1 ]; then
18265                 mdtfree1=$(do_facet $facet \
18266                                 lctl get_param -n osd*.*$mdtname.kbytesfree)
18267                 # decrease in usage by $size_dom from previous
18268                 [ $(($mdtfree1 - $mdtfree2)) -ge $((size_dom / 1024)) ] ||
18269                         error "MDT free space is wrong after removal: " \
18270                               "$mdtfree1 >= $mdtfree2 + $size_dom/1024"
18271         fi
18272
18273         # combined striping
18274         $LFS setstripe -E 1024K -L mdt -E EOF $dom ||
18275                 error "Can't create DoM + OST striping"
18276
18277         size_tmp=2031616 # must be a multiple of PAGE_SIZE=65536 on ARM
18278         dd if=/dev/urandom of=$tmp bs=1024 count=$((size_tmp / 1024))
18279         # check also direct IO along write
18280         dd if=$tmp of=$dom bs=65536 count=$((size_tmp / 65536)) oflag=direct
18281         sync
18282         cmp $tmp $dom || error "file data is different"
18283         [ $(stat -c%s $dom) == $size_tmp ] ||
18284                 error "bad size after write: $(stat -c%s $dom) != $size_tmp"
18285         rm $dom $tmp
18286
18287         return 0
18288 }
18289 run_test 270a "DoM: basic functionality tests"
18290
18291 test_270b() {
18292         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
18293                 skip "Need MDS version at least 2.10.55"
18294
18295         local dom=$DIR/$tdir/dom_file
18296         local max_size=1048576
18297
18298         mkdir -p $DIR/$tdir
18299         $LFS setstripe -E $max_size -L mdt $dom
18300
18301         # truncate over the limit
18302         $TRUNCATE $dom $(($max_size + 1)) &&
18303                 error "successful truncate over the maximum size"
18304         # write over the limit
18305         dd if=/dev/zero of=$dom bs=$max_size seek=1 count=1 &&
18306                 error "successful write over the maximum size"
18307         # append over the limit
18308         dd if=/dev/zero of=$dom bs=$(($max_size - 3)) count=1
18309         echo "12345" >> $dom && error "successful append over the maximum size"
18310         rm $dom
18311
18312         return 0
18313 }
18314 run_test 270b "DoM: maximum size overflow checks for DoM-only file"
18315
18316 test_270c() {
18317         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
18318                 skip "Need MDS version at least 2.10.55"
18319
18320         mkdir -p $DIR/$tdir
18321         $LFS setstripe -E 1024K -L mdt $DIR/$tdir
18322
18323         # check files inherit DoM EA
18324         touch $DIR/$tdir/first
18325         [ $($LFS getstripe -L $DIR/$tdir/first) == "mdt" ] ||
18326                 error "bad pattern"
18327         [ $($LFS getstripe -c $DIR/$tdir/first) == 0 ] ||
18328                 error "bad stripe count"
18329         [ $($LFS getstripe -S $DIR/$tdir/first) == 1048576 ] ||
18330                 error "bad stripe size"
18331
18332         # check directory inherits DoM EA and uses it as default
18333         mkdir $DIR/$tdir/subdir
18334         touch $DIR/$tdir/subdir/second
18335         [ $($LFS getstripe -L $DIR/$tdir/subdir/second) == "mdt" ] ||
18336                 error "bad pattern in sub-directory"
18337         [ $($LFS getstripe -c $DIR/$tdir/subdir/second) == 0 ] ||
18338                 error "bad stripe count in sub-directory"
18339         [ $($LFS getstripe -S $DIR/$tdir/subdir/second) == 1048576 ] ||
18340                 error "bad stripe size in sub-directory"
18341         return 0
18342 }
18343 run_test 270c "DoM: DoM EA inheritance tests"
18344
18345 test_270d() {
18346         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
18347                 skip "Need MDS version at least 2.10.55"
18348
18349         mkdir -p $DIR/$tdir
18350         $LFS setstripe -E 1024K -L mdt $DIR/$tdir
18351
18352         # inherit default DoM striping
18353         mkdir $DIR/$tdir/subdir
18354         touch $DIR/$tdir/subdir/f1
18355
18356         # change default directory striping
18357         $LFS setstripe -c 1 $DIR/$tdir/subdir
18358         touch $DIR/$tdir/subdir/f2
18359         [ $($LFS getstripe -c $DIR/$tdir/subdir/f2) == 1 ] ||
18360                 error "wrong default striping in file 2"
18361         [ $($LFS getstripe -L $DIR/$tdir/subdir/f2) == "raid0" ] ||
18362                 error "bad pattern in file 2"
18363         return 0
18364 }
18365 run_test 270d "DoM: change striping from DoM to RAID0"
18366
18367 test_270e() {
18368         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
18369                 skip "Need MDS version at least 2.10.55"
18370
18371         mkdir -p $DIR/$tdir/dom
18372         mkdir -p $DIR/$tdir/norm
18373         DOMFILES=20
18374         NORMFILES=10
18375         $LFS setstripe -E 1M -L mdt $DIR/$tdir/dom
18376         $LFS setstripe -i 0 -S 2M $DIR/$tdir/norm
18377
18378         createmany -o $DIR/$tdir/dom/dom- $DOMFILES
18379         createmany -o $DIR/$tdir/norm/norm- $NORMFILES
18380
18381         # find DoM files by layout
18382         NUM=$($LFS find -L mdt -type f $DIR/$tdir 2>/dev/null | wc -l)
18383         [ $NUM -eq  $DOMFILES ] ||
18384                 error "lfs find -L: found $NUM, expected $DOMFILES"
18385         echo "Test 1: lfs find 20 DOM files by layout: OK"
18386
18387         # there should be 1 dir with default DOM striping
18388         NUM=$($LFS find -L mdt -type d $DIR/$tdir 2>/dev/null | wc -l)
18389         [ $NUM -eq  1 ] ||
18390                 error "lfs find -L: found $NUM, expected 1 dir"
18391         echo "Test 2: lfs find 1 DOM dir by layout: OK"
18392
18393         # find DoM files by stripe size
18394         NUM=$($LFS find -S -1200K -type f $DIR/$tdir 2>/dev/null | wc -l)
18395         [ $NUM -eq  $DOMFILES ] ||
18396                 error "lfs find -S: found $NUM, expected $DOMFILES"
18397         echo "Test 4: lfs find 20 DOM files by stripe size: OK"
18398
18399         # find files by stripe offset except DoM files
18400         NUM=$($LFS find -i 0 -type f $DIR/$tdir 2>/dev/null | wc -l)
18401         [ $NUM -eq  $NORMFILES ] ||
18402                 error "lfs find -i: found $NUM, expected $NORMFILES"
18403         echo "Test 5: lfs find no DOM files by stripe index: OK"
18404         return 0
18405 }
18406 run_test 270e "DoM: lfs find with DoM files test"
18407
18408 test_270f() {
18409         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
18410                 skip "Need MDS version at least 2.10.55"
18411
18412         local mdtname=${FSNAME}-MDT0000-mdtlov
18413         local dom=$DIR/$tdir/dom_file
18414         local dom_limit_saved=$(do_facet mds1 $LCTL get_param -n \
18415                                                 lod.$mdtname.dom_stripesize)
18416         local dom_limit=131072
18417
18418         do_facet mds1 $LCTL set_param -n lod.$mdtname.dom_stripesize=$dom_limit
18419         local dom_current=$(do_facet mds1 $LCTL get_param -n \
18420                                                 lod.$mdtname.dom_stripesize)
18421         [ ${dom_limit} -eq ${dom_current} ] ||
18422                 error "Cannot change per-MDT DoM stripe limit to $dom_limit"
18423
18424         $LFS mkdir -i 0 -c 1 $DIR/$tdir
18425         $LFS setstripe -d $DIR/$tdir
18426         $LFS setstripe -E $dom_limit -L mdt $DIR/$tdir ||
18427                 error "Can't set directory default striping"
18428
18429         # exceed maximum stripe size
18430         $LFS setstripe -E $((dom_limit * 2)) -L mdt $dom ||
18431                 error "Can't create file with $((dom_limit * 2)) DoM stripe"
18432         [ $($LFS getstripe -S $dom) -eq $((dom_limit * 2)) ] &&
18433                 error "Able to create DoM component size more than LOD limit"
18434
18435         do_facet mds1 $LCTL set_param -n lod.$mdtname.dom_stripesize=0
18436         dom_current=$(do_facet mds1 $LCTL get_param -n \
18437                                                 lod.$mdtname.dom_stripesize)
18438         [ 0 -eq ${dom_current} ] ||
18439                 error "Can't set zero DoM stripe limit"
18440         rm $dom
18441
18442         # attempt to create DoM file on server with disabled DoM should
18443         # remove DoM entry from layout and be succeed
18444         $LFS setstripe -E $dom_limit -L mdt -E -1 $dom ||
18445                 error "Can't create DoM file (DoM is disabled)"
18446         [ $($LFS getstripe -L $dom) == "mdt" ] &&
18447                 error "File has DoM component while DoM is disabled"
18448         rm $dom
18449
18450         # attempt to create DoM file with only DoM stripe should return error
18451         $LFS setstripe -E $dom_limit -L mdt $dom &&
18452                 error "Able to create DoM-only file while DoM is disabled"
18453
18454         # too low values to be aligned with smallest stripe size 64K
18455         do_facet mds1 $LCTL set_param -n lod.$mdtname.dom_stripesize=30000
18456         dom_current=$(do_facet mds1 $LCTL get_param -n \
18457                                                 lod.$mdtname.dom_stripesize)
18458         [ 30000 -eq ${dom_current} ] &&
18459                 error "Can set too small DoM stripe limit"
18460
18461         # 64K is a minimal stripe size in Lustre, expect limit of that size
18462         [ 65536 -eq ${dom_current} ] ||
18463                 error "Limit is not set to 64K but ${dom_current}"
18464
18465         do_facet mds1 $LCTL set_param -n lod.$mdtname.dom_stripesize=2147483648
18466         dom_current=$(do_facet mds1 $LCTL get_param -n \
18467                                                 lod.$mdtname.dom_stripesize)
18468         echo $dom_current
18469         [ 2147483648 -eq ${dom_current} ] &&
18470                 error "Can set too large DoM stripe limit"
18471
18472         do_facet mds1 $LCTL set_param -n \
18473                                 lod.$mdtname.dom_stripesize=$((dom_limit * 2))
18474         $LFS setstripe -E $((dom_limit * 2)) -L mdt $dom ||
18475                 error "Can't create DoM component size after limit change"
18476         do_facet mds1 $LCTL set_param -n \
18477                                 lod.$mdtname.dom_stripesize=$((dom_limit / 2))
18478         $LFS setstripe -E $dom_limit -L mdt ${dom}_big ||
18479                 error "Can't create DoM file after limit decrease"
18480         [ $($LFS getstripe -S ${dom}_big) -eq $((dom_limit / 2)) ] ||
18481                 error "Can create big DoM component after limit decrease"
18482         touch ${dom}_def ||
18483                 error "Can't create file with old default layout"
18484
18485         do_facet mds1 $LCTL set_param -n lod.*.dom_stripesize=$dom_limit_saved
18486         return 0
18487 }
18488 run_test 270f "DoM: maximum DoM stripe size checks"
18489
18490 test_271a() {
18491         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
18492                 skip "Need MDS version at least 2.10.55"
18493
18494         local dom=$DIR/$tdir/dom
18495
18496         mkdir -p $DIR/$tdir
18497
18498         $LFS setstripe -E 1024K -L mdt $dom
18499
18500         lctl set_param -n mdc.*.stats=clear
18501         dd if=/dev/zero of=$dom bs=4096 count=1 || return 1
18502         cat $dom > /dev/null
18503         local reads=$(lctl get_param -n mdc.*.stats | grep -c ost_read)
18504         [ $reads -eq 0 ] || error "Unexpected $reads READ RPCs"
18505         ls $dom
18506         rm -f $dom
18507 }
18508 run_test 271a "DoM: data is cached for read after write"
18509
18510 test_271b() {
18511         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
18512                 skip "Need MDS version at least 2.10.55"
18513
18514         local dom=$DIR/$tdir/dom
18515
18516         mkdir -p $DIR/$tdir
18517
18518         $LFS setstripe -E 1024K -L mdt -E EOF $dom
18519
18520         lctl set_param -n mdc.*.stats=clear
18521         dd if=/dev/zero of=$dom bs=4096 count=1 || return 1
18522         cancel_lru_locks mdc
18523         $CHECKSTAT -t file -s 4096 $dom || error "stat #1 fails"
18524         # second stat to check size is cached on client
18525         $CHECKSTAT -t file -s 4096 $dom || error "stat #2 fails"
18526         local gls=$(lctl get_param -n mdc.*.stats | grep -c ldlm_glimpse)
18527         [ $gls -eq 0 ] || error "Unexpected $gls glimpse RPCs"
18528         rm -f $dom
18529 }
18530 run_test 271b "DoM: no glimpse RPC for stat (DoM only file)"
18531
18532 test_271ba() {
18533         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
18534                 skip "Need MDS version at least 2.10.55"
18535
18536         local dom=$DIR/$tdir/dom
18537
18538         mkdir -p $DIR/$tdir
18539
18540         $LFS setstripe -E 1024K -L mdt -E EOF $dom
18541
18542         lctl set_param -n mdc.*.stats=clear
18543         lctl set_param -n osc.*.stats=clear
18544         dd if=/dev/zero of=$dom bs=2048K count=1 || return 1
18545         cancel_lru_locks mdc
18546         $CHECKSTAT -t file -s 2097152 $dom || error "stat"
18547         # second stat to check size is cached on client
18548         $CHECKSTAT -t file -s 2097152 $dom || error "stat"
18549         local gls=$(lctl get_param -n mdc.*.stats | grep -c ldlm_glimpse)
18550         [ $gls == 0 ] || error "Unexpected $gls glimpse RPCs"
18551         local gls=$(lctl get_param -n osc.*.stats | grep -c ldlm_glimpse)
18552         [ $gls == 0 ] || error "Unexpected $gls OSC glimpse RPCs"
18553         rm -f $dom
18554 }
18555 run_test 271ba "DoM: no glimpse RPC for stat (combined file)"
18556
18557
18558 get_mdc_stats() {
18559         local mdtidx=$1
18560         local param=$2
18561         local mdt=MDT$(printf %04x $mdtidx)
18562
18563         if [ -z $param ]; then
18564                 lctl get_param -n mdc.*$mdt*.stats
18565         else
18566                 lctl get_param -n mdc.*$mdt*.stats | awk "/$param/"'{print $2}'
18567         fi
18568 }
18569
18570 test_271c() {
18571         [ $MDS1_VERSION -lt $(version_code 2.10.55) ] &&
18572                 skip "Need MDS version at least 2.10.55"
18573
18574         local dom=$DIR/$tdir/dom
18575
18576         mkdir -p $DIR/$tdir
18577
18578         $LFS setstripe -E 1024K -L mdt $DIR/$tdir
18579
18580         local mdtidx=$($LFS getstripe -m $DIR/$tdir)
18581         local facet=mds$((mdtidx + 1))
18582
18583         cancel_lru_locks mdc
18584         do_facet $facet lctl set_param -n mdt.*.dom_lock=0
18585         createmany -o $dom 1000
18586         lctl set_param -n mdc.*.stats=clear
18587         smalliomany -w $dom 1000 200
18588         get_mdc_stats $mdtidx
18589         local enq=$(get_mdc_stats $mdtidx ldlm_ibits_enqueue)
18590         # Each file has 1 open, 1 IO enqueues, total 2000
18591         # but now we have also +1 getxattr for security.capability, total 3000
18592         [ $enq -ge 2000 ] || error "Too few enqueues $enq, expected > 2000"
18593         unlinkmany $dom 1000
18594
18595         cancel_lru_locks mdc
18596         do_facet $facet lctl set_param -n mdt.*.dom_lock=1
18597         createmany -o $dom 1000
18598         lctl set_param -n mdc.*.stats=clear
18599         smalliomany -w $dom 1000 200
18600         local enq_2=$(get_mdc_stats $mdtidx ldlm_ibits_enqueue)
18601         # Expect to see reduced amount of RPCs by 1000 due to single enqueue
18602         # for OPEN and IO lock.
18603         [ $((enq - enq_2)) -ge 1000 ] ||
18604                 error "Too many enqueues $enq_2, expected about $((enq - 1000))"
18605         unlinkmany $dom 1000
18606         return 0
18607 }
18608 run_test 271c "DoM: IO lock at open saves enqueue RPCs"
18609
18610 cleanup_271def_tests() {
18611         trap 0
18612         rm -f $1
18613 }
18614
18615 test_271d() {
18616         [ $MDS1_VERSION -lt $(version_code 2.10.57) ] &&
18617                 skip "Need MDS version at least 2.10.57"
18618
18619         local dom=$DIR/$tdir/dom
18620         local tmp=$TMP/$tfile
18621         trap "cleanup_271def_tests $tmp" EXIT
18622
18623         mkdir -p $DIR/$tdir
18624
18625         $LFS setstripe -E 1024K -L mdt $DIR/$tdir
18626
18627         local mdtidx=$($LFS getstripe --mdt-index $DIR/$tdir)
18628
18629         cancel_lru_locks mdc
18630         dd if=/dev/urandom of=$tmp bs=1000 count=1
18631         dd if=$tmp of=$dom bs=1000 count=1
18632         cancel_lru_locks mdc
18633
18634         cat /etc/hosts >> $tmp
18635         lctl set_param -n mdc.*.stats=clear
18636
18637         # append data to the same file it should update local page
18638         echo "Append to the same page"
18639         cat /etc/hosts >> $dom
18640         local num=$(get_mdc_stats $mdtidx ost_read)
18641         local ra=$(get_mdc_stats $mdtidx req_active)
18642         local rw=$(get_mdc_stats $mdtidx req_waittime)
18643
18644         [ -z $num ] || error "$num READ RPC occured"
18645         [ $ra == $rw ] || error "$((ra - rw)) resend occured"
18646         echo "... DONE"
18647
18648         # compare content
18649         cmp $tmp $dom || error "file miscompare"
18650
18651         cancel_lru_locks mdc
18652         lctl set_param -n mdc.*.stats=clear
18653
18654         echo "Open and read file"
18655         cat $dom > /dev/null
18656         local num=$(get_mdc_stats $mdtidx ost_read)
18657         local ra=$(get_mdc_stats $mdtidx req_active)
18658         local rw=$(get_mdc_stats $mdtidx req_waittime)
18659
18660         [ -z $num ] || error "$num READ RPC occured"
18661         [ $ra == $rw ] || error "$((ra - rw)) resend occured"
18662         echo "... DONE"
18663
18664         # compare content
18665         cmp $tmp $dom || error "file miscompare"
18666
18667         return 0
18668 }
18669 run_test 271d "DoM: read on open (1K file in reply buffer)"
18670
18671 test_271f() {
18672         [ $MDS1_VERSION -lt $(version_code 2.10.57) ] &&
18673                 skip "Need MDS version at least 2.10.57"
18674
18675         local dom=$DIR/$tdir/dom
18676         local tmp=$TMP/$tfile
18677         trap "cleanup_271def_tests $tmp" EXIT
18678
18679         mkdir -p $DIR/$tdir
18680
18681         $LFS setstripe -E 1024K -L mdt $DIR/$tdir
18682
18683         local mdtidx=$($LFS getstripe --mdt-index $DIR/$tdir)
18684
18685         cancel_lru_locks mdc
18686         dd if=/dev/urandom of=$tmp bs=265000 count=1
18687         dd if=$tmp of=$dom bs=265000 count=1
18688         cancel_lru_locks mdc
18689         cat /etc/hosts >> $tmp
18690         lctl set_param -n mdc.*.stats=clear
18691
18692         echo "Append to the same page"
18693         cat /etc/hosts >> $dom
18694         local num=$(get_mdc_stats $mdtidx ost_read)
18695         local ra=$(get_mdc_stats $mdtidx req_active)
18696         local rw=$(get_mdc_stats $mdtidx req_waittime)
18697
18698         [ -z $num ] || error "$num READ RPC occured"
18699         [ $ra == $rw ] || error "$((ra - rw)) resend occured"
18700         echo "... DONE"
18701
18702         # compare content
18703         cmp $tmp $dom || error "file miscompare"
18704
18705         cancel_lru_locks mdc
18706         lctl set_param -n mdc.*.stats=clear
18707
18708         echo "Open and read file"
18709         cat $dom > /dev/null
18710         local num=$(get_mdc_stats $mdtidx ost_read)
18711         local ra=$(get_mdc_stats $mdtidx req_active)
18712         local rw=$(get_mdc_stats $mdtidx req_waittime)
18713
18714         [ -z $num ] && num=0
18715         [ $num -eq 1 ] || error "expect 1 READ RPC, $num occured"
18716         [ $ra == $rw ] || error "$((ra - rw)) resend occured"
18717         echo "... DONE"
18718
18719         # compare content
18720         cmp $tmp $dom || error "file miscompare"
18721
18722         return 0
18723 }
18724 run_test 271f "DoM: read on open (200K file and read tail)"
18725
18726 test_271g() {
18727         [[ $($LCTL get_param mdc.*.import) =~ async_discard ]] ||
18728                 skip "Skipping due to old client or server version"
18729
18730         $LFS setstripe -E 1024K -L mdt -E EOF $DIR1/$tfile
18731         # to get layout
18732         $CHECKSTAT -t file $DIR1/$tfile
18733
18734         $MULTIOP $DIR1/$tfile Ow40960_w4096c &
18735         MULTIOP_PID=$!
18736         sleep 1
18737         #define OBD_FAIL_LDLM_CANCEL_BL_CB_RACE
18738         $LCTL set_param fail_loc=0x80000314
18739         rm $DIR1/$tfile || error "Unlink fails"
18740         RC=$?
18741         kill -USR1 $MULTIOP_PID && wait $MULTIOP_PID || error "multiop failure"
18742         [ $RC -eq 0 ] || error "Failed write to stale object"
18743 }
18744 run_test 271g "Discard DoM data vs client flush race"
18745
18746 test_272a() {
18747         [ $MDS1_VERSION -lt $(version_code 2.11.50) ] &&
18748                 skip "Need MDS version at least 2.11.50"
18749
18750         local dom=$DIR/$tdir/dom
18751         mkdir -p $DIR/$tdir
18752
18753         $LFS setstripe -E 256K -L mdt -E -1 -c1 $dom
18754         dd if=/dev/urandom of=$dom bs=512K count=1 ||
18755                 error "failed to write data into $dom"
18756         local old_md5=$(md5sum $dom)
18757
18758         $LFS migrate -E 256K -L mdt -E -1 -c2 $dom ||
18759                 error "failed to migrate to the same DoM component"
18760
18761         local new_md5=$(md5sum $dom)
18762
18763         [ "$old_md5" == "$new_md5" ] ||
18764                 error "md5sum differ: $old_md5, $new_md5"
18765
18766         [ $($LFS getstripe -c $dom) -eq 2 ] ||
18767                 error "migrate stripe count bad: $(LFS getstripe -c $dom) != 2"
18768 }
18769 run_test 272a "DoM migration: new layout with the same DOM component"
18770
18771 test_272b() {
18772         [ $MDS1_VERSION -lt $(version_code 2.11.50) ] &&
18773                 skip "Need MDS version at least 2.11.50"
18774
18775         local dom=$DIR/$tdir/dom
18776         mkdir -p $DIR/$tdir
18777         $LFS setstripe -E 1M -L mdt -E -1 -c1 $dom
18778
18779         local mdtidx=$($LFS getstripe -m $dom)
18780         local mdtname=MDT$(printf %04x $mdtidx)
18781         local facet=mds$((mdtidx + 1))
18782
18783         local mdtfree1=$(do_facet $facet \
18784                 lctl get_param -n osd*.*$mdtname.kbytesfree)
18785         dd if=/dev/urandom of=$dom bs=2M count=1 ||
18786                 error "failed to write data into $dom"
18787         local old_md5=$(md5sum $dom)
18788         cancel_lru_locks mdc
18789         local mdtfree1=$(do_facet $facet \
18790                 lctl get_param -n osd*.*$mdtname.kbytesfree)
18791
18792         $LFS migrate -c2 $dom ||
18793                 error "failed to migrate to the new composite layout"
18794         [ $($LFS getstripe -L $dom) != 'mdt' ] ||
18795                 error "MDT stripe was not removed"
18796
18797         cancel_lru_locks mdc
18798         local new_md5=$(md5sum $dom)
18799         [ "$old_md5" == "$new_md5" ] ||
18800                 error "$old_md5 != $new_md5"
18801
18802         # Skip free space checks with ZFS
18803         if [ "$(facet_fstype $facet)" != "zfs" ]; then
18804                 local mdtfree2=$(do_facet $facet \
18805                                 lctl get_param -n osd*.*$mdtname.kbytesfree)
18806                 [ $mdtfree2 -gt $mdtfree1 ] ||
18807                         error "MDT space is not freed after migration"
18808         fi
18809         return 0
18810 }
18811 run_test 272b "DoM migration: DOM file to the OST-striped file (plain)"
18812
18813 test_272c() {
18814         [ $MDS1_VERSION -lt $(version_code 2.11.50) ] &&
18815                 skip "Need MDS version at least 2.11.50"
18816
18817         local dom=$DIR/$tdir/$tfile
18818         mkdir -p $DIR/$tdir
18819         $LFS setstripe -E 1M -L mdt -E -1 -c1 $dom
18820
18821         local mdtidx=$($LFS getstripe -m $dom)
18822         local mdtname=MDT$(printf %04x $mdtidx)
18823         local facet=mds$((mdtidx + 1))
18824
18825         dd if=/dev/urandom of=$dom bs=2M count=1 oflag=direct ||
18826                 error "failed to write data into $dom"
18827         local old_md5=$(md5sum $dom)
18828         cancel_lru_locks mdc
18829         local mdtfree1=$(do_facet $facet \
18830                 lctl get_param -n osd*.*$mdtname.kbytesfree)
18831
18832         $LFS migrate -E 2M -c1 -E -1 -c2 $dom ||
18833                 error "failed to migrate to the new composite layout"
18834         [ $($LFS getstripe -L $dom) == 'mdt' ] &&
18835                 error "MDT stripe was not removed"
18836
18837         cancel_lru_locks mdc
18838         local new_md5=$(md5sum $dom)
18839         [ "$old_md5" == "$new_md5" ] ||
18840                 error "$old_md5 != $new_md5"
18841
18842         # Skip free space checks with ZFS
18843         if [ "$(facet_fstype $facet)" != "zfs" ]; then
18844                 local mdtfree2=$(do_facet $facet \
18845                                 lctl get_param -n osd*.*$mdtname.kbytesfree)
18846                 [ $mdtfree2 -gt $mdtfree1 ] ||
18847                         error "MDS space is not freed after migration"
18848         fi
18849         return 0
18850 }
18851 run_test 272c "DoM migration: DOM file to the OST-striped file (composite)"
18852
18853 test_272d() {
18854         [ $MDS1_VERSION -lt $(version_code 2.12.55) ] &&
18855                 skip "Need MDS version at least 2.12.55"
18856
18857         local dom=$DIR/$tdir/$tfile
18858         mkdir -p $DIR/$tdir
18859         $LFS setstripe -E 1M -L mdt -E -1 -c1 $dom
18860
18861         local mdtidx=$($LFS getstripe -m $dom)
18862         local mdtname=MDT$(printf %04x $mdtidx)
18863         local facet=mds$((mdtidx + 1))
18864
18865         dd if=/dev/urandom of=$dom bs=2M count=1 oflag=direct ||
18866                 error "failed to write data into $dom"
18867         local old_md5=$(md5sum $dom)
18868         cancel_lru_locks mdc
18869         local mdtfree1=$(do_facet $facet \
18870                 lctl get_param -n osd*.*$mdtname.kbytesfree)
18871
18872         $LFS mirror extend -N -E 2M -c1 -E -1 -c2 $dom ||
18873                 error "failed mirroring to the new composite layout"
18874         $LFS mirror resync $dom ||
18875                 error "failed mirror resync"
18876         $LFS mirror split --mirror-id 1 -d $dom ||
18877                 error "failed mirror split"
18878
18879         [ $($LFS getstripe -L $dom) != 'mdt' ] ||
18880                 error "MDT stripe was not removed"
18881
18882         cancel_lru_locks mdc
18883         local new_md5=$(md5sum $dom)
18884         [ "$old_md5" == "$new_md5" ] ||
18885                 error "$old_md5 != $new_md5"
18886
18887         # Skip free space checks with ZFS
18888         if [ "$(facet_fstype $facet)" != "zfs" ]; then
18889                 local mdtfree2=$(do_facet $facet \
18890                                 lctl get_param -n osd*.*$mdtname.kbytesfree)
18891                 [ $mdtfree2 -gt $mdtfree1 ] ||
18892                         error "MDS space is not freed after DOM mirror deletion"
18893         fi
18894         return 0
18895 }
18896 run_test 272d "DoM mirroring: OST-striped mirror to DOM file"
18897
18898 test_272e() {
18899         [ $MDS1_VERSION -lt $(version_code 2.12.55) ] &&
18900                 skip "Need MDS version at least 2.12.55"
18901
18902         local dom=$DIR/$tdir/$tfile
18903         mkdir -p $DIR/$tdir
18904         $LFS setstripe -c 2 $dom
18905
18906         dd if=/dev/urandom of=$dom bs=512K count=1 oflag=direct ||
18907                 error "failed to write data into $dom"
18908         local old_md5=$(md5sum $dom)
18909         cancel_lru_locks mdc
18910
18911         $LFS mirror extend -N -E 1M -L mdt -E eof -c2 $dom ||
18912                 error "failed mirroring to the DOM layout"
18913         $LFS mirror resync $dom ||
18914                 error "failed mirror resync"
18915         $LFS mirror split --mirror-id 1 -d $dom ||
18916                 error "failed mirror split"
18917
18918         [ $($LFS getstripe -L $dom) != 'mdt' ] ||
18919                 error "MDT stripe was not removed"
18920
18921         cancel_lru_locks mdc
18922         local new_md5=$(md5sum $dom)
18923         [ "$old_md5" == "$new_md5" ] ||
18924                 error "$old_md5 != $new_md5"
18925
18926         return 0
18927 }
18928 run_test 272e "DoM mirroring: DOM mirror to the OST-striped file"
18929
18930 test_272f() {
18931         [ $MDS1_VERSION -lt $(version_code 2.12.55) ] &&
18932                 skip "Need MDS version at least 2.12.55"
18933
18934         local dom=$DIR/$tdir/$tfile
18935         mkdir -p $DIR/$tdir
18936         $LFS setstripe -c 2 $dom
18937
18938         dd if=/dev/urandom of=$dom bs=512K count=1 oflag=direct ||
18939                 error "failed to write data into $dom"
18940         local old_md5=$(md5sum $dom)
18941         cancel_lru_locks mdc
18942
18943         $LFS migrate -E 1M -L mdt -E eof -c2 -v $dom ||
18944                 error "failed migrating to the DOM file"
18945
18946         cancel_lru_locks mdc
18947         local new_md5=$(md5sum $dom)
18948         [ "$old_md5" != "$new_md5" ] &&
18949                 error "$old_md5 != $new_md5"
18950
18951         return 0
18952 }
18953 run_test 272f "DoM migration: OST-striped file to DOM file"
18954
18955 test_273a() {
18956         [ $MDS1_VERSION -lt $(version_code 2.11.50) ] &&
18957                 skip "Need MDS version at least 2.11.50"
18958
18959         # Layout swap cannot be done if either file has DOM component,
18960         # this will never be supported, migration should be used instead
18961
18962         local dom=$DIR/$tdir/$tfile
18963         mkdir -p $DIR/$tdir
18964
18965         $LFS setstripe -c2 ${dom}_plain
18966         $LFS setstripe -E 1M -L mdt -E -1 -c2 ${dom}_dom
18967         $LFS swap_layouts ${dom}_plain ${dom}_dom &&
18968                 error "can swap layout with DoM component"
18969         $LFS swap_layouts ${dom}_dom ${dom}_plain &&
18970                 error "can swap layout with DoM component"
18971
18972         $LFS setstripe -E 1M -c1 -E -1 -c2 ${dom}_comp
18973         $LFS swap_layouts ${dom}_comp ${dom}_dom &&
18974                 error "can swap layout with DoM component"
18975         $LFS swap_layouts ${dom}_dom ${dom}_comp &&
18976                 error "can swap layout with DoM component"
18977         return 0
18978 }
18979 run_test 273a "DoM: layout swapping should fail with DOM"
18980
18981 test_275() {
18982         remote_ost_nodsh && skip "remote OST with nodsh"
18983         [ $OST1_VERSION -lt $(version_code 2.10.57) ] &&
18984                 skip "Need OST version >= 2.10.57"
18985
18986         local file=$DIR/$tfile
18987         local oss
18988
18989         oss=$(comma_list $(osts_nodes))
18990
18991         dd if=/dev/urandom of=$file bs=1M count=2 ||
18992                 error "failed to create a file"
18993         cancel_lru_locks osc
18994
18995         #lock 1
18996         dd if=$file of=/dev/null bs=1M count=1 iflag=direct ||
18997                 error "failed to read a file"
18998
18999 #define OBD_FAIL_LDLM_PAUSE_CANCEL2      0x31f
19000         $LCTL set_param fail_loc=0x8000031f
19001
19002         cancel_lru_locks osc &
19003         sleep 1
19004
19005 #define OBD_FAIL_LDLM_PROLONG_PAUSE      0x32b
19006         do_nodes $oss $LCTL set_param fail_loc=0x8000032b
19007         #IO takes another lock, but matches the PENDING one
19008         #and places it to the IO RPC
19009         dd if=$file of=/dev/null bs=1M count=1 iflag=direct ||
19010                 error "failed to read a file with PENDING lock"
19011 }
19012 run_test 275 "Read on a canceled duplicate lock"
19013
19014 test_276() {
19015         remote_ost_nodsh && skip "remote OST with nodsh"
19016         local pid
19017
19018         do_facet ost1 "(while true; do \
19019                 $LCTL get_param obdfilter.*.filesfree > /dev/null 2>&1; \
19020                 done) & pid=\\\$!; echo \\\$pid > $TMP/sanity_276_pid" &
19021         pid=$!
19022
19023         for LOOP in $(seq 20); do
19024                 stop ost1
19025                 start ost1 $(ostdevname 1) $OST_MOUNT_OPTS
19026         done
19027         kill -9 $pid
19028         do_facet ost1 "pid=\\\$(cat $TMP/sanity_276_pid); kill -9 \\\$pid; \
19029                 rm $TMP/sanity_276_pid"
19030 }
19031 run_test 276 "Race between mount and obd_statfs"
19032
19033 test_277() {
19034         $LCTL set_param ldlm.namespaces.*.lru_size=0
19035         dd if=/dev/zero of=$DIR/$tfile bs=1M count=1
19036         local cached_mb=$($LCTL get_param llite.*.max_cached_mb |
19037                         grep ^used_mb | awk '{print $2}')
19038         [ $cached_mb -eq 1 ] || error "expected mb 1 got $cached_mb"
19039         dd if=/dev/zero of=$DIR/$tfile bs=1M count=1 \
19040                 oflag=direct conv=notrunc
19041         cached_mb=$($LCTL get_param llite.*.max_cached_mb |
19042                         grep ^used_mb | awk '{print $2}')
19043         [ $cached_mb -eq 0 ] || error "expected mb 0 got $cached_mb"
19044 }
19045 run_test 277 "Direct IO shall drop page cache"
19046
19047 test_278() {
19048         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
19049         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs" && return
19050         [[ "$(facet_host mds1)" != "$(facet_host mds2)" ]] &&
19051                 skip "needs the same host for mdt1 mdt2" && return
19052
19053         local pid1
19054         local pid2
19055
19056 #define OBD_FAIL_OBD_STOP_MDS_RACE     0x60b
19057         do_facet mds2 $LCTL set_param fail_loc=0x8000060c
19058         stop mds2 &
19059         pid2=$!
19060
19061         stop mds1
19062
19063         echo "Starting MDTs"
19064         start mds1 $(mdsdevname 1) $MDS_MOUNT_OPTS
19065         wait $pid2
19066 #For the error assertion will happen. lu_env_get_key(..., &mdt_thread_key)
19067 #will return NULL
19068         do_facet mds2 $LCTL set_param fail_loc=0
19069
19070         start mds2 $(mdsdevname 2) $MDS_MOUNT_OPTS
19071         wait_recovery_complete mds2
19072 }
19073 run_test 278 "Race starting MDS between MDTs stop/start"
19074
19075 cleanup_test_300() {
19076         trap 0
19077         umask $SAVE_UMASK
19078 }
19079 test_striped_dir() {
19080         local mdt_index=$1
19081         local stripe_count
19082         local stripe_index
19083
19084         mkdir -p $DIR/$tdir
19085
19086         SAVE_UMASK=$(umask)
19087         trap cleanup_test_300 RETURN EXIT
19088
19089         $LFS setdirstripe -i $mdt_index -c 2 -H all_char -o 755 \
19090                                                 $DIR/$tdir/striped_dir ||
19091                 error "set striped dir error"
19092
19093         local mode=$(stat -c%a $DIR/$tdir/striped_dir)
19094         [ "$mode" = "755" ] || error "expect 755 got $mode"
19095
19096         $LFS getdirstripe $DIR/$tdir/striped_dir > /dev/null 2>&1 ||
19097                 error "getdirstripe failed"
19098         stripe_count=$($LFS getdirstripe -c $DIR/$tdir/striped_dir)
19099         if [ "$stripe_count" != "2" ]; then
19100                 error "1:stripe_count is $stripe_count, expect 2"
19101         fi
19102         stripe_count=$($LFS getdirstripe -T $DIR/$tdir/striped_dir)
19103         if [ "$stripe_count" != "2" ]; then
19104                 error "2:stripe_count is $stripe_count, expect 2"
19105         fi
19106
19107         stripe_index=$($LFS getdirstripe -i $DIR/$tdir/striped_dir)
19108         if [ "$stripe_index" != "$mdt_index" ]; then
19109                 error "stripe_index is $stripe_index, expect $mdt_index"
19110         fi
19111
19112         [ $(stat -c%h $DIR/$tdir/striped_dir) == '2' ] ||
19113                 error "nlink error after create striped dir"
19114
19115         mkdir $DIR/$tdir/striped_dir/a
19116         mkdir $DIR/$tdir/striped_dir/b
19117
19118         stat $DIR/$tdir/striped_dir/a ||
19119                 error "create dir under striped dir failed"
19120         stat $DIR/$tdir/striped_dir/b ||
19121                 error "create dir under striped dir failed"
19122
19123         [ $(stat -c%h $DIR/$tdir/striped_dir) == '4' ] ||
19124                 error "nlink error after mkdir"
19125
19126         rmdir $DIR/$tdir/striped_dir/a
19127         [ $(stat -c%h $DIR/$tdir/striped_dir) == '3' ] ||
19128                 error "nlink error after rmdir"
19129
19130         rmdir $DIR/$tdir/striped_dir/b
19131         [ $(stat -c%h $DIR/$tdir/striped_dir) == '2' ] ||
19132                 error "nlink error after rmdir"
19133
19134         chattr +i $DIR/$tdir/striped_dir
19135         createmany -o $DIR/$tdir/striped_dir/f 10 &&
19136                 error "immutable flags not working under striped dir!"
19137         chattr -i $DIR/$tdir/striped_dir
19138
19139         rmdir $DIR/$tdir/striped_dir ||
19140                 error "rmdir striped dir error"
19141
19142         cleanup_test_300
19143
19144         true
19145 }
19146
19147 test_300a() {
19148         [ $MDS1_VERSION -lt $(version_code 2.7.0) ] &&
19149                 skip "skipped for lustre < 2.7.0"
19150         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19151         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19152
19153         test_striped_dir 0 || error "failed on striped dir on MDT0"
19154         test_striped_dir 1 || error "failed on striped dir on MDT0"
19155 }
19156 run_test 300a "basic striped dir sanity test"
19157
19158 test_300b() {
19159         [ $MDS1_VERSION -lt $(version_code 2.7.0) ] &&
19160                 skip "skipped for lustre < 2.7.0"
19161         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19162         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19163
19164         local i
19165         local mtime1
19166         local mtime2
19167         local mtime3
19168
19169         test_mkdir $DIR/$tdir || error "mkdir fail"
19170         $LFS setdirstripe -i 0 -c 2 -H all_char $DIR/$tdir/striped_dir ||
19171                 error "set striped dir error"
19172         for i in {0..9}; do
19173                 mtime1=$(stat -c %Y $DIR/$tdir/striped_dir)
19174                 sleep 1
19175                 touch $DIR/$tdir/striped_dir/file_$i || error "touch error $i"
19176                 mtime2=$(stat -c %Y $DIR/$tdir/striped_dir)
19177                 [ $mtime1 -eq $mtime2 ] && error "mtime unchanged after create"
19178                 sleep 1
19179                 rm -f $DIR/$tdir/striped_dir/file_$i || error "unlink error $i"
19180                 mtime3=$(stat -c %Y $DIR/$tdir/striped_dir)
19181                 [ $mtime2 -eq $mtime3 ] && error "mtime unchanged after unlink"
19182         done
19183         true
19184 }
19185 run_test 300b "check ctime/mtime for striped dir"
19186
19187 test_300c() {
19188         [ $MDS1_VERSION -lt $(version_code 2.7.0) ] &&
19189                 skip "skipped for lustre < 2.7.0"
19190         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19191         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19192
19193         local file_count
19194
19195         mkdir -p $DIR/$tdir
19196         $LFS setdirstripe -i 0 -c 2 $DIR/$tdir/striped_dir ||
19197                 error "set striped dir error"
19198
19199         chown $RUNAS_ID:$RUNAS_GID $DIR/$tdir/striped_dir ||
19200                 error "chown striped dir failed"
19201
19202         $RUNAS createmany -o $DIR/$tdir/striped_dir/f 5000 ||
19203                 error "create 5k files failed"
19204
19205         file_count=$(ls $DIR/$tdir/striped_dir | wc -l)
19206
19207         [ "$file_count" = 5000 ] || error "file count $file_count != 5000"
19208
19209         rm -rf $DIR/$tdir
19210 }
19211 run_test 300c "chown && check ls under striped directory"
19212
19213 test_300d() {
19214         [ $MDS1_VERSION -lt $(version_code 2.7.0) ] &&
19215                 skip "skipped for lustre < 2.7.0"
19216         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19217         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19218
19219         local stripe_count
19220         local file
19221
19222         mkdir -p $DIR/$tdir
19223         $LFS setstripe -c 2 $DIR/$tdir
19224
19225         #local striped directory
19226         $LFS setdirstripe -i 0 -c 2 -H all_char $DIR/$tdir/striped_dir ||
19227                 error "set striped dir error"
19228         createmany -o $DIR/$tdir/striped_dir/f 10 ||
19229                 error "create 10 files failed"
19230
19231         #remote striped directory
19232         $LFS setdirstripe -i 1 -c 2 $DIR/$tdir/remote_striped_dir ||
19233                 error "set striped dir error"
19234         createmany -o $DIR/$tdir/remote_striped_dir/f 10 ||
19235                 error "create 10 files failed"
19236
19237         for file in $(find $DIR/$tdir); do
19238                 stripe_count=$($LFS getstripe -c $file)
19239                 [ $stripe_count -eq 2 ] ||
19240                         error "wrong stripe $stripe_count for $file"
19241         done
19242
19243         rm -rf $DIR/$tdir
19244 }
19245 run_test 300d "check default stripe under striped directory"
19246
19247 test_300e() {
19248         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19249                 skip "Need MDS version at least 2.7.55"
19250         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19251         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19252
19253         local stripe_count
19254         local file
19255
19256         mkdir -p $DIR/$tdir
19257
19258         $LFS setdirstripe -i 0 -c 2 -H all_char $DIR/$tdir/striped_dir ||
19259                 error "set striped dir error"
19260
19261         touch $DIR/$tdir/striped_dir/a
19262         touch $DIR/$tdir/striped_dir/b
19263         touch $DIR/$tdir/striped_dir/c
19264
19265         mkdir $DIR/$tdir/striped_dir/dir_a
19266         mkdir $DIR/$tdir/striped_dir/dir_b
19267         mkdir $DIR/$tdir/striped_dir/dir_c
19268
19269         $LFS setdirstripe -i 0 -c 2 -H all_char $DIR/$tdir/striped_dir/stp_a ||
19270                 error "set striped adir under striped dir error"
19271
19272         $LFS setdirstripe -i 0 -c 2 -H all_char $DIR/$tdir/striped_dir/stp_b ||
19273                 error "set striped bdir under striped dir error"
19274
19275         $LFS setdirstripe -i 0 -c 2 -H all_char $DIR/$tdir/striped_dir/stp_c ||
19276                 error "set striped cdir under striped dir error"
19277
19278         mrename $DIR/$tdir/striped_dir/dir_a $DIR/$tdir/striped_dir/dir_b ||
19279                 error "rename dir under striped dir fails"
19280
19281         mrename $DIR/$tdir/striped_dir/stp_a $DIR/$tdir/striped_dir/stp_b ||
19282                 error "rename dir under different stripes fails"
19283
19284         mrename $DIR/$tdir/striped_dir/a $DIR/$tdir/striped_dir/c ||
19285                 error "rename file under striped dir should succeed"
19286
19287         mrename $DIR/$tdir/striped_dir/dir_b $DIR/$tdir/striped_dir/dir_c ||
19288                 error "rename dir under striped dir should succeed"
19289
19290         rm -rf $DIR/$tdir
19291 }
19292 run_test 300e "check rename under striped directory"
19293
19294 test_300f() {
19295         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19296         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19297         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19298                 skip "Need MDS version at least 2.7.55"
19299
19300         local stripe_count
19301         local file
19302
19303         rm -rf $DIR/$tdir
19304         mkdir -p $DIR/$tdir
19305
19306         $LFS setdirstripe -i 0 -c 2 -H all_char $DIR/$tdir/striped_dir ||
19307                 error "set striped dir error"
19308
19309         $LFS setdirstripe -i 0 -c 2 -H all_char $DIR/$tdir/striped_dir1 ||
19310                 error "set striped dir error"
19311
19312         touch $DIR/$tdir/striped_dir/a
19313         mkdir $DIR/$tdir/striped_dir/dir_a
19314         $LFS setdirstripe -i 0 -c 2 $DIR/$tdir/striped_dir/stp_a ||
19315                 error "create striped dir under striped dir fails"
19316
19317         touch $DIR/$tdir/striped_dir1/b
19318         mkdir $DIR/$tdir/striped_dir1/dir_b
19319         $LFS setdirstripe -i 0 -c 2 $DIR/$tdir/striped_dir/stp_b ||
19320                 error "create striped dir under striped dir fails"
19321
19322         mrename $DIR/$tdir/striped_dir/dir_a $DIR/$tdir/striped_dir1/dir_b ||
19323                 error "rename dir under different striped dir should fail"
19324
19325         mrename $DIR/$tdir/striped_dir/stp_a $DIR/$tdir/striped_dir1/stp_b ||
19326                 error "rename striped dir under diff striped dir should fail"
19327
19328         mrename $DIR/$tdir/striped_dir/a $DIR/$tdir/striped_dir1/a ||
19329                 error "rename file under diff striped dirs fails"
19330
19331         rm -rf $DIR/$tdir
19332 }
19333 run_test 300f "check rename cross striped directory"
19334
19335 test_300_check_default_striped_dir()
19336 {
19337         local dirname=$1
19338         local default_count=$2
19339         local default_index=$3
19340         local stripe_count
19341         local stripe_index
19342         local dir_stripe_index
19343         local dir
19344
19345         echo "checking $dirname $default_count $default_index"
19346         $LFS setdirstripe -D -c $default_count -i $default_index \
19347                                 -t all_char $DIR/$tdir/$dirname ||
19348                 error "set default stripe on striped dir error"
19349         stripe_count=$($LFS getdirstripe -D -c $DIR/$tdir/$dirname)
19350         [ $stripe_count -eq $default_count ] ||
19351                 error "expect $default_count get $stripe_count for $dirname"
19352
19353         stripe_index=$($LFS getdirstripe -D -i $DIR/$tdir/$dirname)
19354         [ $stripe_index -eq $default_index ] ||
19355                 error "expect $default_index get $stripe_index for $dirname"
19356
19357         mkdir $DIR/$tdir/$dirname/{test1,test2,test3,test4} ||
19358                                                 error "create dirs failed"
19359
19360         createmany -o $DIR/$tdir/$dirname/f- 10 || error "create files failed"
19361         unlinkmany $DIR/$tdir/$dirname/f- 10    || error "unlink files failed"
19362         for dir in $(find $DIR/$tdir/$dirname/*); do
19363                 stripe_count=$($LFS getdirstripe -c $dir)
19364                 [ $stripe_count -eq $default_count ] ||
19365                 [ $stripe_count -eq 0 ] || [ $default_count -eq 1 ] ||
19366                 error "stripe count $default_count != $stripe_count for $dir"
19367
19368                 stripe_index=$($LFS getdirstripe -i $dir)
19369                 [ $default_index -eq -1 ] ||
19370                         [ $stripe_index -eq $default_index ] ||
19371                         error "$stripe_index != $default_index for $dir"
19372
19373                 #check default stripe
19374                 stripe_count=$($LFS getdirstripe -D -c $dir)
19375                 [ $stripe_count -eq $default_count ] ||
19376                 error "default count $default_count != $stripe_count for $dir"
19377
19378                 stripe_index=$($LFS getdirstripe -D -i $dir)
19379                 [ $stripe_index -eq $default_index ] ||
19380                 error "default index $default_index != $stripe_index for $dir"
19381         done
19382         rmdir $DIR/$tdir/$dirname/* || error "rmdir failed"
19383 }
19384
19385 test_300g() {
19386         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19387         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19388                 skip "Need MDS version at least 2.7.55"
19389
19390         local dir
19391         local stripe_count
19392         local stripe_index
19393
19394         mkdir $DIR/$tdir
19395         mkdir $DIR/$tdir/normal_dir
19396
19397         #Checking when client cache stripe index
19398         $LFS setdirstripe -c$MDSCOUNT $DIR/$tdir/striped_dir
19399         $LFS setdirstripe -D -i1 $DIR/$tdir/striped_dir ||
19400                 error "create striped_dir failed"
19401
19402         $LFS setdirstripe -i0 $DIR/$tdir/striped_dir/dir0 ||
19403                 error "create dir0 fails"
19404         stripe_index=$($LFS getdirstripe -i $DIR/$tdir/striped_dir/dir0)
19405         [ $stripe_index -eq 0 ] ||
19406                 error "dir0 expect index 0 got $stripe_index"
19407
19408         mkdir $DIR/$tdir/striped_dir/dir1 ||
19409                 error "create dir1 fails"
19410         stripe_index=$($LFS getdirstripe -i $DIR/$tdir/striped_dir/dir1)
19411         [ $stripe_index -eq 1 ] ||
19412                 error "dir1 expect index 1 got $stripe_index"
19413
19414         #check default stripe count/stripe index
19415         test_300_check_default_striped_dir normal_dir $MDSCOUNT 1
19416         test_300_check_default_striped_dir normal_dir 1 0
19417         test_300_check_default_striped_dir normal_dir 2 1
19418         test_300_check_default_striped_dir normal_dir 2 -1
19419
19420         #delete default stripe information
19421         echo "delete default stripeEA"
19422         $LFS setdirstripe -d $DIR/$tdir/normal_dir ||
19423                 error "set default stripe on striped dir error"
19424
19425         mkdir -p $DIR/$tdir/normal_dir/{test1,test2,test3,test4}
19426         for dir in $(find $DIR/$tdir/normal_dir/*); do
19427                 stripe_count=$($LFS getdirstripe -c $dir)
19428                 [ $stripe_count -eq 0 ] ||
19429                         error "expect 1 get $stripe_count for $dir"
19430                 stripe_index=$($LFS getdirstripe -i $dir)
19431                 [ $stripe_index -eq 0 ] ||
19432                         error "expect 0 get $stripe_index for $dir"
19433         done
19434 }
19435 run_test 300g "check default striped directory for normal directory"
19436
19437 test_300h() {
19438         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19439         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19440                 skip "Need MDS version at least 2.7.55"
19441
19442         local dir
19443         local stripe_count
19444
19445         mkdir $DIR/$tdir
19446         $LFS setdirstripe -i0 -c$MDSCOUNT -H all_char $DIR/$tdir/striped_dir ||
19447                 error "set striped dir error"
19448
19449         test_300_check_default_striped_dir striped_dir $MDSCOUNT 1
19450         test_300_check_default_striped_dir striped_dir 1 0
19451         test_300_check_default_striped_dir striped_dir 2 1
19452         test_300_check_default_striped_dir striped_dir 2 -1
19453
19454         #delete default stripe information
19455         $LFS setdirstripe -d $DIR/$tdir/striped_dir ||
19456                 error "set default stripe on striped dir error"
19457
19458         mkdir -p $DIR/$tdir/striped_dir/{test1,test2,test3,test4}
19459         for dir in $(find $DIR/$tdir/striped_dir/*); do
19460                 stripe_count=$($LFS getdirstripe -c $dir)
19461                 [ $stripe_count -eq 0 ] ||
19462                         error "expect 1 get $stripe_count for $dir"
19463         done
19464 }
19465 run_test 300h "check default striped directory for striped directory"
19466
19467 test_300i() {
19468         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19469         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19470         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19471                 skip "Need MDS version at least 2.7.55"
19472
19473         local stripe_count
19474         local file
19475
19476         mkdir $DIR/$tdir
19477
19478         $LFS setdirstripe -i 0 -c$MDSCOUNT -H all_char $DIR/$tdir/striped_dir ||
19479                 error "set striped dir error"
19480
19481         createmany -o $DIR/$tdir/striped_dir/f- 10 ||
19482                 error "create files under striped dir failed"
19483
19484         $LFS setdirstripe -i0 -c$MDSCOUNT -H all_char $DIR/$tdir/hashdir ||
19485                 error "set striped hashdir error"
19486
19487         $LFS setdirstripe -i0 -c$MDSCOUNT -H all_char $DIR/$tdir/hashdir/d0 ||
19488                 error "create dir0 under hash dir failed"
19489         $LFS setdirstripe -i0 -c$MDSCOUNT -H fnv_1a_64 $DIR/$tdir/hashdir/d1 ||
19490                 error "create dir1 under hash dir failed"
19491
19492         # unfortunately, we need to umount to clear dir layout cache for now
19493         # once we fully implement dir layout, we can drop this
19494         umount_client $MOUNT || error "umount failed"
19495         mount_client $MOUNT || error "mount failed"
19496
19497         $LFS find -H fnv_1a_64 $DIR/$tdir/hashdir
19498         local dircnt=$($LFS find -H fnv_1a_64 $DIR/$tdir/hashdir | wc -l)
19499         [ $dircnt -eq 1 ] || error "lfs find striped dir got:$dircnt,except:1"
19500
19501         #set the stripe to be unknown hash type
19502         #define OBD_FAIL_UNKNOWN_LMV_STRIPE     0x1901
19503         $LCTL set_param fail_loc=0x1901
19504         for ((i = 0; i < 10; i++)); do
19505                 $CHECKSTAT -t file $DIR/$tdir/striped_dir/f-$i ||
19506                         error "stat f-$i failed"
19507                 rm $DIR/$tdir/striped_dir/f-$i || error "unlink f-$i failed"
19508         done
19509
19510         touch $DIR/$tdir/striped_dir/f0 &&
19511                 error "create under striped dir with unknown hash should fail"
19512
19513         $LCTL set_param fail_loc=0
19514
19515         umount_client $MOUNT || error "umount failed"
19516         mount_client $MOUNT || error "mount failed"
19517
19518         return 0
19519 }
19520 run_test 300i "client handle unknown hash type striped directory"
19521
19522 test_300j() {
19523         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19524         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19525         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19526                 skip "Need MDS version at least 2.7.55"
19527
19528         local stripe_count
19529         local file
19530
19531         mkdir $DIR/$tdir
19532
19533         #define OBD_FAIL_SPLIT_UPDATE_REC       0x1702
19534         $LCTL set_param fail_loc=0x1702
19535         $LFS setdirstripe -i 0 -c$MDSCOUNT -H all_char $DIR/$tdir/striped_dir ||
19536                 error "set striped dir error"
19537
19538         createmany -o $DIR/$tdir/striped_dir/f- 10 ||
19539                 error "create files under striped dir failed"
19540
19541         $LCTL set_param fail_loc=0
19542
19543         rm -rf $DIR/$tdir || error "unlink striped dir fails"
19544
19545         return 0
19546 }
19547 run_test 300j "test large update record"
19548
19549 test_300k() {
19550         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19551         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19552         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19553                 skip "Need MDS version at least 2.7.55"
19554
19555         # this test needs a huge transaction
19556         local kb
19557         kb=$(do_facet $SINGLEMDS lctl get_param -n osd*.lustre-MDT0000.kbytestotal)
19558         [ $kb -lt $((1024*1024)) ] && skip "too small mds: $kb"
19559
19560         local stripe_count
19561         local file
19562
19563         mkdir $DIR/$tdir
19564
19565         #define OBD_FAIL_LARGE_STRIPE   0x1703
19566         $LCTL set_param fail_loc=0x1703
19567         $LFS setdirstripe -i 0 -c192 $DIR/$tdir/striped_dir ||
19568                 error "set striped dir error"
19569         $LCTL set_param fail_loc=0
19570
19571         $LFS getdirstripe $DIR/$tdir/striped_dir ||
19572                 error "getstripeddir fails"
19573         rm -rf $DIR/$tdir/striped_dir ||
19574                 error "unlink striped dir fails"
19575
19576         return 0
19577 }
19578 run_test 300k "test large striped directory"
19579
19580 test_300l() {
19581         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19582         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19583         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19584                 skip "Need MDS version at least 2.7.55"
19585
19586         local stripe_index
19587
19588         test_mkdir -p $DIR/$tdir/striped_dir
19589         chown $RUNAS_ID $DIR/$tdir/striped_dir ||
19590                         error "chown $RUNAS_ID failed"
19591         $LFS setdirstripe -i 1 -D $DIR/$tdir/striped_dir ||
19592                 error "set default striped dir failed"
19593
19594         #define OBD_FAIL_MDS_STALE_DIR_LAYOUT    0x158
19595         $LCTL set_param fail_loc=0x80000158
19596         $RUNAS mkdir $DIR/$tdir/striped_dir/test_dir || error "create dir fails"
19597
19598         stripe_index=$($LFS getdirstripe -i $DIR/$tdir/striped_dir/test_dir)
19599         [ $stripe_index -eq 1 ] ||
19600                 error "expect 1 get $stripe_index for $dir"
19601 }
19602 run_test 300l "non-root user to create dir under striped dir with stale layout"
19603
19604 test_300m() {
19605         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19606         [ $MDSCOUNT -ge 2 ] && skip_env "Only for single MDT"
19607         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19608                 skip "Need MDS version at least 2.7.55"
19609
19610         mkdir -p $DIR/$tdir/striped_dir
19611         $LFS setdirstripe -D -c 1 $DIR/$tdir/striped_dir ||
19612                 error "set default stripes dir error"
19613
19614         mkdir $DIR/$tdir/striped_dir/a || error "mkdir a fails"
19615
19616         stripe_count=$($LFS getdirstripe -c $DIR/$tdir/striped_dir/a)
19617         [ $stripe_count -eq 0 ] ||
19618                         error "expect 0 get $stripe_count for a"
19619
19620         $LFS setdirstripe -D -c 2 $DIR/$tdir/striped_dir ||
19621                 error "set default stripes dir error"
19622
19623         mkdir $DIR/$tdir/striped_dir/b || error "mkdir b fails"
19624
19625         stripe_count=$($LFS getdirstripe -c $DIR/$tdir/striped_dir/b)
19626         [ $stripe_count -eq 0 ] ||
19627                         error "expect 0 get $stripe_count for b"
19628
19629         $LFS setdirstripe -D -c1 -i2 $DIR/$tdir/striped_dir ||
19630                 error "set default stripes dir error"
19631
19632         mkdir $DIR/$tdir/striped_dir/c &&
19633                 error "default stripe_index is invalid, mkdir c should fails"
19634
19635         rm -rf $DIR/$tdir || error "rmdir fails"
19636 }
19637 run_test 300m "setstriped directory on single MDT FS"
19638
19639 cleanup_300n() {
19640         local list=$(comma_list $(mdts_nodes))
19641
19642         trap 0
19643         do_nodes $list $LCTL set_param -n mdt.*.enable_remote_dir_gid=0
19644 }
19645
19646 test_300n() {
19647         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19648         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19649         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19650                 skip "Need MDS version at least 2.7.55"
19651         remote_mds_nodsh && skip "remote MDS with nodsh"
19652
19653         local stripe_index
19654         local list=$(comma_list $(mdts_nodes))
19655
19656         trap cleanup_300n RETURN EXIT
19657         mkdir -p $DIR/$tdir
19658         chmod 777 $DIR/$tdir
19659         $RUNAS $LFS setdirstripe -i0 -c$MDSCOUNT \
19660                                 $DIR/$tdir/striped_dir > /dev/null 2>&1 &&
19661                 error "create striped dir succeeds with gid=0"
19662
19663         do_nodes $list $LCTL set_param -n mdt.*.enable_remote_dir_gid=-1
19664         $RUNAS $LFS setdirstripe -i0 -c$MDSCOUNT $DIR/$tdir/striped_dir ||
19665                 error "create striped dir fails with gid=-1"
19666
19667         do_nodes $list $LCTL set_param -n mdt.*.enable_remote_dir_gid=0
19668         $RUNAS $LFS setdirstripe -i 1 -c$MDSCOUNT -D \
19669                                 $DIR/$tdir/striped_dir > /dev/null 2>&1 &&
19670                 error "set default striped dir succeeds with gid=0"
19671
19672
19673         do_nodes $list $LCTL set_param -n mdt.*.enable_remote_dir_gid=-1
19674         $RUNAS $LFS setdirstripe -i 1 -c$MDSCOUNT -D $DIR/$tdir/striped_dir ||
19675                 error "set default striped dir fails with gid=-1"
19676
19677
19678         do_nodes $list $LCTL set_param -n mdt.*.enable_remote_dir_gid=0
19679         $RUNAS mkdir $DIR/$tdir/striped_dir/test_dir ||
19680                                         error "create test_dir fails"
19681         $RUNAS mkdir $DIR/$tdir/striped_dir/test_dir1 ||
19682                                         error "create test_dir1 fails"
19683         $RUNAS mkdir $DIR/$tdir/striped_dir/test_dir2 ||
19684                                         error "create test_dir2 fails"
19685         cleanup_300n
19686 }
19687 run_test 300n "non-root user to create dir under striped dir with default EA"
19688
19689 test_300o() {
19690         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19691         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19692         [ $MDS1_VERSION -lt $(version_code 2.7.55) ] &&
19693                 skip "Need MDS version at least 2.7.55"
19694
19695         local numfree1
19696         local numfree2
19697
19698         mkdir -p $DIR/$tdir
19699
19700         numfree1=$(lctl get_param -n mdc.*MDT0000*.filesfree)
19701         numfree2=$(lctl get_param -n mdc.*MDT0001*.filesfree)
19702         if [ $numfree1 -lt 66000 ] || [ $numfree2 -lt 66000 ]; then
19703                 skip "not enough free inodes $numfree1 $numfree2"
19704         fi
19705
19706         numfree1=$(lctl get_param -n mdc.*MDT0000-mdc-*.kbytesfree)
19707         numfree2=$(lctl get_param -n mdc.*MDT0001-mdc-*.kbytesfree)
19708         if [ $numfree1 -lt 300000 ] || [ $numfree2 -lt 300000 ]; then
19709                 skip "not enough free space $numfree1 $numfree2"
19710         fi
19711
19712         $LFS setdirstripe -c2 $DIR/$tdir/striped_dir ||
19713                 error "setdirstripe fails"
19714
19715         createmany -d $DIR/$tdir/striped_dir/d 131000 ||
19716                 error "create dirs fails"
19717
19718         $LCTL set_param ldlm.namespaces.*mdc-*.lru_size=0
19719         ls $DIR/$tdir/striped_dir > /dev/null ||
19720                 error "ls striped dir fails"
19721         unlinkmany -d $DIR/$tdir/striped_dir/d 131000 ||
19722                 error "unlink big striped dir fails"
19723 }
19724 run_test 300o "unlink big sub stripe(> 65000 subdirs)"
19725
19726 test_300p() {
19727         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19728         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19729         remote_mds_nodsh && skip "remote MDS with nodsh"
19730
19731         mkdir -p $DIR/$tdir
19732
19733         #define OBD_FAIL_OUT_ENOSPC     0x1704
19734         do_facet mds2 lctl set_param fail_loc=0x80001704
19735         $LFS setdirstripe -i 0 -c2 $DIR/$tdir/bad_striped_dir > /dev/null 2>&1 \
19736                  && error "create striped directory should fail"
19737
19738         [ -e $DIR/$tdir/bad_striped_dir ] && error "striped dir exists"
19739
19740         $LFS setdirstripe -c2 $DIR/$tdir/bad_striped_dir
19741         true
19742 }
19743 run_test 300p "create striped directory without space"
19744
19745 test_300q() {
19746         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19747         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
19748
19749         local fd=$(free_fd)
19750         local cmd="exec $fd<$tdir"
19751         cd $DIR
19752         $LFS mkdir -c $MDSCOUNT $tdir || error "create $tdir fails"
19753         eval $cmd
19754         cmd="exec $fd<&-"
19755         trap "eval $cmd" EXIT
19756         cd $tdir || error "cd $tdir fails"
19757         rmdir  ../$tdir || error "rmdir $tdir fails"
19758         mkdir local_dir && error "create dir succeeds"
19759         $LFS setdirstripe -i1 remote_dir && error "create remote dir succeeds"
19760         eval $cmd
19761         return 0
19762 }
19763 run_test 300q "create remote directory under orphan directory"
19764
19765 test_300r() {
19766         [ $(lustre_version_code $SINGLEMDS) -lt $(version_code 2.7.55) ] &&
19767                 skip "Need MDS version at least 2.7.55" && return
19768         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs" && return
19769
19770         mkdir $DIR/$tdir
19771
19772         $LFS setdirstripe -i 0 -c -1 $DIR/$tdir/striped_dir ||
19773                 error "set striped dir error"
19774
19775         $LFS getdirstripe $DIR/$tdir/striped_dir ||
19776                 error "getstripeddir fails"
19777
19778         local stripe_count
19779         stripe_count=$($LFS getdirstripe $DIR/$tdir/striped_dir |
19780                       awk '/lmv_stripe_count:/ { print $2 }')
19781
19782         [ $MDSCOUNT -ne $stripe_count ] &&
19783                 error "wrong stripe count $stripe_count expected $MDSCOUNT"
19784
19785         rm -rf $DIR/$tdir/striped_dir ||
19786                 error "unlink striped dir fails"
19787 }
19788 run_test 300r "test -1 striped directory"
19789
19790 prepare_remote_file() {
19791         mkdir $DIR/$tdir/src_dir ||
19792                 error "create remote source failed"
19793
19794         cp /etc/hosts $DIR/$tdir/src_dir/a ||
19795                  error "cp to remote source failed"
19796         touch $DIR/$tdir/src_dir/a
19797
19798         $LFS mkdir -i 1 $DIR/$tdir/tgt_dir ||
19799                 error "create remote target dir failed"
19800
19801         touch $DIR/$tdir/tgt_dir/b
19802
19803         mrename $DIR/$tdir/src_dir/a $DIR/$tdir/tgt_dir/b ||
19804                 error "rename dir cross MDT failed!"
19805
19806         $CHECKSTAT -t file $DIR/$tdir/src_dir/a &&
19807                 error "src_child still exists after rename"
19808
19809         $CHECKSTAT -t file $DIR/$tdir/tgt_dir/b ||
19810                 error "missing file(a) after rename"
19811
19812         diff /etc/hosts $DIR/$tdir/tgt_dir/b ||
19813                 error "diff after rename"
19814 }
19815
19816 test_310a() {
19817         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 4 MDTs"
19818         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19819
19820         local remote_file=$DIR/$tdir/tgt_dir/b
19821
19822         mkdir -p $DIR/$tdir
19823
19824         prepare_remote_file || error "prepare remote file failed"
19825
19826         #open-unlink file
19827         $OPENUNLINK $remote_file $remote_file ||
19828                 error "openunlink $remote_file failed"
19829         $CHECKSTAT -a $remote_file || error "$remote_file exists"
19830 }
19831 run_test 310a "open unlink remote file"
19832
19833 test_310b() {
19834         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 4 MDTs"
19835         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19836
19837         local remote_file=$DIR/$tdir/tgt_dir/b
19838
19839         mkdir -p $DIR/$tdir
19840
19841         prepare_remote_file || error "prepare remote file failed"
19842
19843         ln $remote_file $DIR/$tfile || error "link failed for remote file"
19844         $MULTIOP $DIR/$tfile Ouc || error "mulitop failed"
19845         $CHECKSTAT -t file $remote_file || error "check file failed"
19846 }
19847 run_test 310b "unlink remote file with multiple links while open"
19848
19849 test_310c() {
19850         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19851         [[ $MDSCOUNT -lt 4 ]] && skip_env "needs >= 4 MDTs"
19852
19853         local remote_file=$DIR/$tdir/tgt_dir/b
19854
19855         mkdir -p $DIR/$tdir
19856
19857         prepare_remote_file || error "prepare remote file failed"
19858
19859         ln $remote_file $DIR/$tfile || error "link failed for remote file"
19860         multiop_bg_pause $remote_file O_uc ||
19861                         error "mulitop failed for remote file"
19862         MULTIPID=$!
19863         $MULTIOP $DIR/$tfile Ouc
19864         kill -USR1 $MULTIPID
19865         wait $MULTIPID
19866 }
19867 run_test 310c "open-unlink remote file with multiple links"
19868
19869 #LU-4825
19870 test_311() {
19871         [ $PARALLEL == "yes" ] && skip "skip parallel run"
19872         [ $OSTCOUNT -lt 2 ] && skip "needs >= 2 OSTs"
19873         [ $MDS1_VERSION -lt $(version_code 2.8.54) ] &&
19874                 skip "lustre < 2.8.54 does not contain LU-4825 fix"
19875         remote_mds_nodsh && skip "remote MDS with nodsh"
19876
19877         local old_iused=$($LFS df -i | grep OST0000 | awk '{ print $3 }')
19878         local mdts=$(comma_list $(mdts_nodes))
19879
19880         mkdir -p $DIR/$tdir
19881         $LFS setstripe -i 0 -c 1 $DIR/$tdir
19882         createmany -o $DIR/$tdir/$tfile. 1000
19883
19884         # statfs data is not real time, let's just calculate it
19885         old_iused=$((old_iused + 1000))
19886
19887         local count=$(do_facet $SINGLEMDS "$LCTL get_param -n \
19888                         osp.*OST0000*MDT0000.create_count")
19889         local max_count=$(do_facet $SINGLEMDS "$LCTL get_param -n \
19890                                 osp.*OST0000*MDT0000.max_create_count")
19891         do_nodes $mdts "$LCTL set_param -n osp.*OST0000*.max_create_count=0"
19892
19893         $LFS setstripe -i 0 $DIR/$tdir/$tfile || error "setstripe failed"
19894         local index=$($LFS getstripe -i $DIR/$tdir/$tfile)
19895         [ $index -ne 0 ] || error "$tfile stripe index is 0"
19896
19897         unlinkmany $DIR/$tdir/$tfile. 1000
19898
19899         do_nodes $mdts "$LCTL set_param -n \
19900                         osp.*OST0000*.max_create_count=$max_count"
19901         [ $MDS1_VERSION -lt $(version_code 2.12.51) ] &&
19902                 do_nodes $mdts "$LCTL set_param -n \
19903                                 osp.*OST0000*.create_count=$count"
19904         do_nodes $mdts "$LCTL get_param osp.*OST0000*.create_count" |
19905                         grep "=0" && error "create_count is zero"
19906
19907         local new_iused
19908         for i in $(seq 120); do
19909                 new_iused=$($LFS df -i | grep OST0000 | awk '{ print $3 }')
19910                 # system may be too busy to destroy all objs in time, use
19911                 # a somewhat small value to not fail autotest
19912                 [ $((old_iused - new_iused)) -gt 400 ] && break
19913                 sleep 1
19914         done
19915
19916         echo "waited $i sec, old Iused $old_iused, new Iused $new_iused"
19917         [ $((old_iused - new_iused)) -gt 400 ] ||
19918                 error "objs not destroyed after unlink"
19919 }
19920 run_test 311 "disable OSP precreate, and unlink should destroy objs"
19921
19922 zfs_oid_to_objid()
19923 {
19924         local ost=$1
19925         local objid=$2
19926
19927         local vdevdir=$(dirname $(facet_vdevice $ost))
19928         local cmd="$ZDB -e -p $vdevdir -ddddd $(facet_device $ost)"
19929         local zfs_zapid=$(do_facet $ost $cmd |
19930                           grep -w "/O/0/d$((objid%32))" -C 5 |
19931                           awk '/Object/{getline; print $1}')
19932         local zfs_objid=$(do_facet $ost $cmd $zfs_zapid |
19933                           awk "/$objid = /"'{printf $3}')
19934
19935         echo $zfs_objid
19936 }
19937
19938 zfs_object_blksz() {
19939         local ost=$1
19940         local objid=$2
19941
19942         local vdevdir=$(dirname $(facet_vdevice $ost))
19943         local cmd="$ZDB -e -p $vdevdir -dddd $(facet_device $ost)"
19944         local blksz=$(do_facet $ost $cmd $objid |
19945                       awk '/dblk/{getline; printf $4}')
19946
19947         case "${blksz: -1}" in
19948                 k|K) blksz=$((${blksz:0:$((${#blksz} - 1))}*1024)) ;;
19949                 m|M) blksz=$((${blksz:0:$((${#blksz} - 1))}*1024*1024)) ;;
19950                 *) ;;
19951         esac
19952
19953         echo $blksz
19954 }
19955
19956 test_312() { # LU-4856
19957         remote_ost_nodsh && skip "remote OST with nodsh"
19958         [ "$ost1_FSTYPE" = "zfs" ] ||
19959                 skip_env "the test only applies to zfs"
19960
19961         local max_blksz=$(do_facet ost1 \
19962                           $ZFS get -p recordsize $(facet_device ost1) |
19963                           awk '!/VALUE/{print $3}')
19964
19965         # to make life a little bit easier
19966         $LFS mkdir -c 1 -i 0 $DIR/$tdir
19967         $LFS setstripe -c 1 -i 0 $DIR/$tdir
19968
19969         local tf=$DIR/$tdir/$tfile
19970         touch $tf
19971         local oid=$($LFS getstripe $tf | awk '/obdidx/{getline; print $2}')
19972
19973         # Get ZFS object id
19974         local zfs_objid=$(zfs_oid_to_objid ost1 $oid)
19975         # block size change by sequential overwrite
19976         local bs
19977
19978         for ((bs=$PAGE_SIZE; bs <= max_blksz; bs *= 4)) ; do
19979                 dd if=/dev/zero of=$tf bs=$bs count=1 oflag=sync conv=notrunc
19980
19981                 local blksz=$(zfs_object_blksz ost1 $zfs_objid)
19982                 [ $blksz -eq $bs ] || error "blksz error: $blksz, expected: $bs"
19983         done
19984         rm -f $tf
19985
19986         # block size change by sequential append write
19987         dd if=/dev/zero of=$tf bs=$PAGE_SIZE count=1 oflag=sync conv=notrunc
19988         oid=$($LFS getstripe $tf | awk '/obdidx/{getline; print $2}')
19989         zfs_objid=$(zfs_oid_to_objid ost1 $oid)
19990         local count
19991
19992         for ((count = 1; count < $((max_blksz / PAGE_SIZE)); count *= 2)); do
19993                 dd if=/dev/zero of=$tf bs=$PAGE_SIZE count=$count seek=$count \
19994                         oflag=sync conv=notrunc
19995
19996                 blksz=$(zfs_object_blksz ost1 $zfs_objid)
19997                 [ $blksz -eq $((2 * count * PAGE_SIZE)) ] ||
19998                         error "blksz error, actual $blksz, " \
19999                                 "expected: 2 * $count * $PAGE_SIZE"
20000         done
20001         rm -f $tf
20002
20003         # random write
20004         touch $tf
20005         oid=$($LFS getstripe $tf | awk '/obdidx/{getline; print $2}')
20006         zfs_objid=$(zfs_oid_to_objid ost1 $oid)
20007
20008         dd if=/dev/zero of=$tf bs=1K count=1 oflag=sync conv=notrunc
20009         blksz=$(zfs_object_blksz ost1 $zfs_objid)
20010         [ $blksz -eq $PAGE_SIZE ] ||
20011                 error "blksz error: $blksz, expected: $PAGE_SIZE"
20012
20013         dd if=/dev/zero of=$tf bs=64K count=1 oflag=sync conv=notrunc seek=128
20014         blksz=$(zfs_object_blksz ost1 $zfs_objid)
20015         [ $blksz -eq 65536 ] || error "blksz error: $blksz, expected: 64k"
20016
20017         dd if=/dev/zero of=$tf bs=1M count=1 oflag=sync conv=notrunc
20018         blksz=$(zfs_object_blksz ost1 $zfs_objid)
20019         [ $blksz -eq 65536 ] || error "rewrite error: $blksz, expected: 64k"
20020 }
20021 run_test 312 "make sure ZFS adjusts its block size by write pattern"
20022
20023 test_313() {
20024         remote_ost_nodsh && skip "remote OST with nodsh"
20025
20026         local file=$DIR/$tfile
20027
20028         rm -f $file
20029         $LFS setstripe -c 1 -i 0 $file || error "setstripe failed"
20030
20031         # define OBD_FAIL_TGT_RCVD_EIO           0x720
20032         do_facet ost1 "$LCTL set_param fail_loc=0x720"
20033         dd if=/dev/zero of=$file bs=$PAGE_SIZE oflag=direct count=1 &&
20034                 error "write should failed"
20035         do_facet ost1 "$LCTL set_param fail_loc=0"
20036         rm -f $file
20037 }
20038 run_test 313 "io should fail after last_rcvd update fail"
20039
20040 test_314() {
20041         [ $OSTCOUNT -lt 2 ] && skip "needs >= 2 OSTs"
20042
20043         $LFS setstripe -c 2 -i 0 $DIR/$tfile || error "setstripe failed"
20044         do_facet ost1 "$LCTL set_param fail_loc=0x720"
20045         rm -f $DIR/$tfile
20046         wait_delete_completed
20047         do_facet ost1 "$LCTL set_param fail_loc=0"
20048 }
20049 run_test 314 "OSP shouldn't fail after last_rcvd update failure"
20050
20051 test_315() { # LU-618
20052         [ -f /proc/$$/io ] || skip_env "no IO accounting in kernel"
20053
20054         local file=$DIR/$tfile
20055         rm -f $file
20056
20057         $MULTIOP $file oO_CREAT:O_DIRECT:O_RDWR:w4063232c ||
20058                 error "multiop file write failed"
20059         $MULTIOP $file oO_RDONLY:r4063232_c &
20060         PID=$!
20061
20062         sleep 2
20063
20064         local rbytes=$(awk '/read_bytes/ { print $2 }' /proc/$PID/io)
20065         kill -USR1 $PID
20066
20067         [ $rbytes -gt 4000000 ] || error "read is not accounted ($rbytes)"
20068         rm -f $file
20069 }
20070 run_test 315 "read should be accounted"
20071
20072 test_316() {
20073         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs"
20074         large_xattr_enabled || skip_env "ea_inode feature disabled"
20075
20076         rm -rf $DIR/$tdir/d
20077         mkdir -p $DIR/$tdir/d
20078         chown nobody $DIR/$tdir/d
20079         touch $DIR/$tdir/d/file
20080
20081         $LFS mv -M1 $DIR/$tdir/d || error "lfs mv failed"
20082 }
20083 run_test 316 "lfs mv"
20084
20085 test_317() {
20086         [ $MDS1_VERSION -lt $(version_code 2.11.53) ] &&
20087                 skip "Need MDS version at least 2.11.53"
20088         if [ "$ost1_FSTYPE" == "zfs" ]; then
20089                 skip "LU-10370: no implementation for ZFS"
20090         fi
20091
20092         local trunc_sz
20093         local grant_blk_size
20094
20095         grant_blk_size=$($LCTL get_param osc.$FSNAME*.import |
20096                         awk '/grant_block_size:/ { print $2; exit; }')
20097         #
20098         # Create File of size 5M. Truncate it to below size's and verify
20099         # blocks count.
20100         #
20101         dd if=/dev/zero of=$DIR/$tfile bs=5M count=1 conv=fsync ||
20102                 error "Create file $DIR/$tfile failed"
20103         stack_trap "rm -f $DIR/$tfile" EXIT
20104
20105         for trunc_sz in 2097152 4097 4000 509 0; do
20106                 $TRUNCATE $DIR/$tfile $trunc_sz ||
20107                         error "truncate $tfile to $trunc_sz failed"
20108                 local sz=$(stat --format=%s $DIR/$tfile)
20109                 local blk=$(stat --format=%b $DIR/$tfile)
20110                 local trunc_blk=$((((trunc_sz + (grant_blk_size - 1) ) /
20111                                      grant_blk_size) * 8))
20112
20113                 if [[ $blk -ne $trunc_blk ]]; then
20114                         $(which stat) $DIR/$tfile
20115                         error "Expected Block $trunc_blk got $blk for $tfile"
20116                 fi
20117
20118                 $CHECKSTAT -s $trunc_sz $DIR/$tfile ||
20119                         error "Expected Size $trunc_sz got $sz for $tfile"
20120         done
20121
20122         #
20123         # sparse file test
20124         # Create file with a hole and write actual two blocks. Block count
20125         # must be 16.
20126         #
20127         dd if=/dev/zero of=$DIR/$tfile bs=$grant_blk_size count=2 seek=5 \
20128                 conv=fsync || error "Create file : $DIR/$tfile"
20129
20130         # Calculate the final truncate size.
20131         trunc_sz=$(($(stat --format=%s $DIR/$tfile) - (grant_blk_size + 1)))
20132
20133         #
20134         # truncate to size $trunc_sz bytes. Strip the last block
20135         # The block count must drop to 8
20136         #
20137         $TRUNCATE $DIR/$tfile $trunc_sz ||
20138                 error "truncate $tfile to $trunc_sz failed"
20139
20140         local trunc_bsz=$((grant_blk_size / $(stat --format=%B $DIR/$tfile)))
20141         sz=$(stat --format=%s $DIR/$tfile)
20142         blk=$(stat --format=%b $DIR/$tfile)
20143
20144         if [[ $blk -ne $trunc_bsz ]]; then
20145                 $(which stat) $DIR/$tfile
20146                 error "Expected Block $trunc_bsz got $blk for $tfile"
20147         fi
20148
20149         $CHECKSTAT -s $trunc_sz $DIR/$tfile ||
20150                 error "Expected Size $trunc_sz got $sz for $tfile"
20151 }
20152 run_test 317 "Verify blocks get correctly update after truncate"
20153
20154 test_318() {
20155         local old_max_active=$($LCTL get_param -n \
20156                             llite.*.max_read_ahead_async_active 2>/dev/null)
20157
20158         $LCTL set_param llite.*.max_read_ahead_async_active=256
20159         local max_active=$($LCTL get_param -n \
20160                            llite.*.max_read_ahead_async_active 2>/dev/null)
20161         [ $max_active -ne 256 ] && error "expected 256 but got $max_active"
20162
20163         # currently reset to 0 is unsupported, leave it 512 for now.
20164         $LCTL set_param llite.*.max_read_ahead_async_active=0 &&
20165                 error "set max_read_ahead_async_active should fail"
20166
20167         $LCTL set_param llite.*.max_read_ahead_async_active=512
20168         max_active=$($LCTL get_param -n \
20169                      llite.*.max_read_ahead_async_active 2>/dev/null)
20170         [ $max_active -eq 512 ] || error "expected 512 but got $max_active"
20171
20172         # restore @max_active
20173         [ $old_max_active -ne 0 ] && $LCTL set_param \
20174                 llite.*.max_read_ahead_async_active=$old_max_active
20175
20176         local old_threshold=$($LCTL get_param -n \
20177                 llite.*.read_ahead_async_file_threshold_mb 2>/dev/null)
20178         local max_per_file_mb=$($LCTL get_param -n \
20179                 llite.*.max_read_ahead_per_file_mb 2>/dev/null)
20180
20181         local invalid=$(($max_per_file_mb + 1))
20182         $LCTL set_param \
20183                 llite.*.read_ahead_async_file_threshold_mb=$invalid\
20184                         && error "set $invalid should fail"
20185
20186         local valid=$(($invalid - 1))
20187         $LCTL set_param \
20188                 llite.*.read_ahead_async_file_threshold_mb=$valid ||
20189                         error "set $valid should succeed"
20190         local threshold=$($LCTL get_param -n \
20191                 llite.*.read_ahead_async_file_threshold_mb 2>/dev/null)
20192         [ $threshold -eq $valid ] || error \
20193                 "expect threshold $valid got $threshold"
20194         $LCTL set_param \
20195                 llite.*.read_ahead_async_file_threshold_mb=$old_threshold
20196 }
20197 run_test 318 "Verify async readahead tunables"
20198
20199 test_319() {
20200         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs" && return 0
20201
20202         local before=$(date +%s)
20203         local evict
20204         local mdir=$DIR/$tdir
20205         local file=$mdir/xxx
20206
20207         $LFS mkdir -i0 $mdir || error "mkdir $mdir fails"
20208         touch $file
20209
20210 #define OBD_FAIL_LDLM_LOCAL_CANCEL_PAUSE 0x32c
20211         $LCTL set_param fail_val=5 fail_loc=0x8000032c
20212         $LFS mv -m1 $file &
20213
20214         sleep 1
20215         dd if=$file of=/dev/null
20216         wait
20217         evict=$($LCTL get_param mdc.$FSNAME-MDT*.state |
20218           awk -F"[ [,]" '/EVICTED ]$/ { if (mx<$5) {mx=$5;} } END { print mx }')
20219
20220         [ -z "$evict" ] || [[ $evict -le $before ]] || error "eviction happened"
20221 }
20222 run_test 319 "lost lease lock on migrate error"
20223
20224 test_fake_rw() {
20225         local read_write=$1
20226         if [ "$read_write" = "write" ]; then
20227                 local dd_cmd="dd if=/dev/zero of=$DIR/$tfile"
20228         elif [ "$read_write" = "read" ]; then
20229                 local dd_cmd="dd of=/dev/null if=$DIR/$tfile"
20230         else
20231                 error "argument error"
20232         fi
20233
20234         # turn off debug for performance testing
20235         local saved_debug=$($LCTL get_param -n debug)
20236         $LCTL set_param debug=0
20237
20238         $LFS setstripe -c 1 -i 0 $DIR/$tfile
20239
20240         # get ost1 size - lustre-OST0000
20241         local ost1_avail_size=$($LFS df | awk /${ost1_svc}/'{ print $4 }')
20242         local blocks=$((ost1_avail_size/2/1024)) # half avail space by megabytes
20243         [ $blocks -gt 1000 ] && blocks=1000 # 1G in maximum
20244
20245         if [ "$read_write" = "read" ]; then
20246                 truncate -s $(expr 1048576 \* $blocks) $DIR/$tfile
20247         fi
20248
20249         local start_time=$(date +%s.%N)
20250         $dd_cmd bs=1M count=$blocks oflag=sync ||
20251                 error "real dd $read_write error"
20252         local duration=$(bc <<< "$(date +%s.%N) - $start_time")
20253
20254         if [ "$read_write" = "write" ]; then
20255                 rm -f $DIR/$tfile
20256         fi
20257
20258         # define OBD_FAIL_OST_FAKE_RW           0x238
20259         do_facet ost1 $LCTL set_param fail_loc=0x238
20260
20261         local start_time=$(date +%s.%N)
20262         $dd_cmd bs=1M count=$blocks oflag=sync ||
20263                 error "fake dd $read_write error"
20264         local duration_fake=$(bc <<< "$(date +%s.%N) - $start_time")
20265
20266         if [ "$read_write" = "write" ]; then
20267                 # verify file size
20268                 cancel_lru_locks osc
20269                 $CHECKSTAT -t file -s $((blocks * 1024 * 1024)) $DIR/$tfile ||
20270                         error "$tfile size not $blocks MB"
20271         fi
20272         do_facet ost1 $LCTL set_param fail_loc=0
20273
20274         echo "fake $read_write $duration_fake vs. normal $read_write" \
20275                 "$duration in seconds"
20276         [ $(bc <<< "$duration_fake < $duration") -eq 1 ] ||
20277                 error_not_in_vm "fake write is slower"
20278
20279         $LCTL set_param -n debug="$saved_debug"
20280         rm -f $DIR/$tfile
20281 }
20282 test_399a() { # LU-7655 for OST fake write
20283         remote_ost_nodsh && skip "remote OST with nodsh"
20284
20285         test_fake_rw write
20286 }
20287 run_test 399a "fake write should not be slower than normal write"
20288
20289 test_399b() { # LU-8726 for OST fake read
20290         remote_ost_nodsh && skip "remote OST with nodsh"
20291         if [ "$ost1_FSTYPE" != "ldiskfs" ]; then
20292                 skip_env "ldiskfs only test"
20293         fi
20294
20295         test_fake_rw read
20296 }
20297 run_test 399b "fake read should not be slower than normal read"
20298
20299 test_400a() { # LU-1606, was conf-sanity test_74
20300         if ! which $CC > /dev/null 2>&1; then
20301                 skip_env "$CC is not installed"
20302         fi
20303
20304         local extra_flags=''
20305         local out=$TMP/$tfile
20306         local prefix=/usr/include/lustre
20307         local prog
20308
20309         if ! [[ -d $prefix ]]; then
20310                 # Assume we're running in tree and fixup the include path.
20311                 extra_flags+=" -I$LUSTRE/../lnet/include/uapi -I$LUSTRE/include/uapi -I$LUSTRE/include"
20312                 extra_flags+=" -L$LUSTRE/utils/.lib"
20313         fi
20314
20315         for prog in $LUSTRE_TESTS_API_DIR/*.c; do
20316                 $CC -Wall -Werror $extra_flags -o $out $prog -llustreapi ||
20317                         error "client api broken"
20318         done
20319         rm -f $out
20320 }
20321 run_test 400a "Lustre client api program can compile and link"
20322
20323 test_400b() { # LU-1606, LU-5011
20324         local header
20325         local out=$TMP/$tfile
20326         local prefix=/usr/include/linux/lustre
20327
20328         # We use a hard coded prefix so that this test will not fail
20329         # when run in tree. There are headers in lustre/include/lustre/
20330         # that are not packaged (like lustre_idl.h) and have more
20331         # complicated include dependencies (like config.h and lnet/types.h).
20332         # Since this test about correct packaging we just skip them when
20333         # they don't exist (see below) rather than try to fixup cppflags.
20334
20335         if ! which $CC > /dev/null 2>&1; then
20336                 skip_env "$CC is not installed"
20337         fi
20338
20339         for header in $prefix/*.h; do
20340                 if ! [[ -f "$header" ]]; then
20341                         continue
20342                 fi
20343
20344                 if [[ "$(basename $header)" == lustre_ioctl.h ]]; then
20345                         continue # lustre_ioctl.h is internal header
20346                 fi
20347
20348                 $CC -Wall -Werror -include $header -c -x c /dev/null -o $out ||
20349                         error "cannot compile '$header'"
20350         done
20351         rm -f $out
20352 }
20353 run_test 400b "packaged headers can be compiled"
20354
20355 test_401a() { #LU-7437
20356         local printf_arg=$(find -printf 2>&1 | grep "unrecognized:")
20357         [ -n "$printf_arg" ] && skip_env "find does not support -printf"
20358
20359         #count the number of parameters by "list_param -R"
20360         local params=$($LCTL list_param -R '*' 2>/dev/null | wc -l)
20361         #count the number of parameters by listing proc files
20362         local proc_dirs=$(eval \ls -d $proc_regexp 2>/dev/null)
20363         echo "proc_dirs='$proc_dirs'"
20364         [ -n "$proc_dirs" ] || error "no proc_dirs on $HOSTNAME"
20365         local procs=$(find -L $proc_dirs -mindepth 1 -printf '%P\n' 2>/dev/null|
20366                       sort -u | wc -l)
20367
20368         [ $params -eq $procs ] ||
20369                 error "found $params parameters vs. $procs proc files"
20370
20371         # test the list_param -D option only returns directories
20372         params=$($LCTL list_param -R -D '*' 2>/dev/null | wc -l)
20373         #count the number of parameters by listing proc directories
20374         procs=$(find -L $proc_dirs -mindepth 1 -type d -printf '%P\n' 2>/dev/null |
20375                 sort -u | wc -l)
20376
20377         [ $params -eq $procs ] ||
20378                 error "found $params parameters vs. $procs proc files"
20379 }
20380 run_test 401a "Verify if 'lctl list_param -R' can list parameters recursively"
20381
20382 test_401b() {
20383         local save=$($LCTL get_param -n jobid_var)
20384         local tmp=testing
20385
20386         $LCTL set_param foo=bar jobid_var=$tmp bar=baz &&
20387                 error "no error returned when setting bad parameters"
20388
20389         local jobid_new=$($LCTL get_param -n foe jobid_var baz)
20390         [[ "$jobid_new" == "$tmp" ]] || error "jobid tmp $jobid_new != $tmp"
20391
20392         $LCTL set_param -n fog=bam jobid_var=$save bat=fog
20393         local jobid_old=$($LCTL get_param -n foe jobid_var bag)
20394         [[ "$jobid_old" == "$save" ]] || error "jobid new $jobid_old != $save"
20395 }
20396 run_test 401b "Verify 'lctl {get,set}_param' continue after error"
20397
20398 test_401c() {
20399         local jobid_var_old=$($LCTL get_param -n jobid_var)
20400         local jobid_var_new
20401
20402         $LCTL set_param jobid_var= &&
20403                 error "no error returned for 'set_param a='"
20404
20405         jobid_var_new=$($LCTL get_param -n jobid_var)
20406         [[ "$jobid_var_old" == "$jobid_var_new" ]] ||
20407                 error "jobid_var was changed by setting without value"
20408
20409         $LCTL set_param jobid_var &&
20410                 error "no error returned for 'set_param a'"
20411
20412         jobid_var_new=$($LCTL get_param -n jobid_var)
20413         [[ "$jobid_var_old" == "$jobid_var_new" ]] ||
20414                 error "jobid_var was changed by setting without value"
20415 }
20416 run_test 401c "Verify 'lctl set_param' without value fails in either format."
20417
20418 test_401d() {
20419         local jobid_var_old=$($LCTL get_param -n jobid_var)
20420         local jobid_var_new
20421         local new_value="foo=bar"
20422
20423         $LCTL set_param jobid_var=$new_value ||
20424                 error "'set_param a=b' did not accept a value containing '='"
20425
20426         jobid_var_new=$($LCTL get_param -n jobid_var)
20427         [[ "$jobid_var_new" == "$new_value" ]] ||
20428                 error "'set_param a=b' failed on a value containing '='"
20429
20430         # Reset the jobid_var to test the other format
20431         $LCTL set_param jobid_var=$jobid_var_old
20432         jobid_var_new=$($LCTL get_param -n jobid_var)
20433         [[ "$jobid_var_new" == "$jobid_var_old" ]] ||
20434                 error "failed to reset jobid_var"
20435
20436         $LCTL set_param jobid_var $new_value ||
20437                 error "'set_param a b' did not accept a value containing '='"
20438
20439         jobid_var_new=$($LCTL get_param -n jobid_var)
20440         [[ "$jobid_var_new" == "$new_value" ]] ||
20441                 error "'set_param a b' failed on a value containing '='"
20442
20443         $LCTL set_param jobid_var $jobid_var_old
20444         jobid_var_new=$($LCTL get_param -n jobid_var)
20445         [[ "$jobid_var_new" == "$jobid_var_old" ]] ||
20446                 error "failed to reset jobid_var"
20447 }
20448 run_test 401d "Verify 'lctl set_param' accepts values containing '='"
20449
20450 test_402() {
20451         [[ $MDS1_VERSION -ge $(version_code 2.7.66) ]] ||
20452         [[ $MDS1_VERSION -ge $(version_code 2.7.18.4) &&
20453                 $MDS1_VERSION -lt $(version_code 2.7.50) ]] ||
20454         [[ $MDS1_VERSION -ge $(version_code 2.7.2) &&
20455                 $MDS1_VERSION -lt $(version_code 2.7.11) ]] ||
20456                 skip "Need MDS version 2.7.2+ or 2.7.18.4+ or 2.7.66+"
20457         remote_mds_nodsh && skip "remote MDS with nodsh"
20458
20459         $LFS setdirstripe -i 0 $DIR/$tdir || error "setdirstripe -i 0 failed"
20460 #define OBD_FAIL_MDS_FLD_LOOKUP 0x15c
20461         do_facet mds1 "lctl set_param fail_loc=0x8000015c"
20462         touch $DIR/$tdir/$tfile && error "touch should fail with ENOENT" ||
20463                 echo "Touch failed - OK"
20464 }
20465 run_test 402 "Return ENOENT to lod_generate_and_set_lovea"
20466
20467 test_403() {
20468         local file1=$DIR/$tfile.1
20469         local file2=$DIR/$tfile.2
20470         local tfile=$TMP/$tfile
20471
20472         rm -f $file1 $file2 $tfile
20473
20474         touch $file1
20475         ln $file1 $file2
20476
20477         # 30 sec OBD_TIMEOUT in ll_getattr()
20478         # right before populating st_nlink
20479         $LCTL set_param fail_loc=0x80001409
20480         stat -c %h $file1 > $tfile &
20481
20482         # create an alias, drop all locks and reclaim the dentry
20483         < $file2
20484         cancel_lru_locks mdc
20485         cancel_lru_locks osc
20486         sysctl -w vm.drop_caches=2
20487
20488         wait
20489
20490         [ $(cat $tfile) -gt 0 ] || error "wrong nlink count: $(cat $tfile)"
20491
20492         rm -f $tfile $file1 $file2
20493 }
20494 run_test 403 "i_nlink should not drop to zero due to aliasing"
20495
20496 test_404() { # LU-6601
20497         [[ $MDS1_VERSION -ge $(version_code 2.8.53) ]] ||
20498                 skip "Need server version newer than 2.8.52"
20499         remote_mds_nodsh && skip "remote MDS with nodsh"
20500
20501         local mosps=$(do_facet $SINGLEMDS $LCTL dl |
20502                 awk '/osp .*-osc-MDT/ { print $4}')
20503
20504         local osp
20505         for osp in $mosps; do
20506                 echo "Deactivate: " $osp
20507                 do_facet $SINGLEMDS $LCTL --device %$osp deactivate
20508                 local stat=$(do_facet $SINGLEMDS $LCTL dl |
20509                         awk -vp=$osp '$4 == p { print $2 }')
20510                 [ $stat = IN ] || {
20511                         do_facet $SINGLEMDS $LCTL dl | grep -w $osp
20512                         error "deactivate error"
20513                 }
20514                 echo "Activate: " $osp
20515                 do_facet $SINGLEMDS $LCTL --device %$osp activate
20516                 local stat=$(do_facet $SINGLEMDS $LCTL dl |
20517                         awk -vp=$osp '$4 == p { print $2 }')
20518                 [ $stat = UP ] || {
20519                         do_facet $SINGLEMDS $LCTL dl | grep -w $osp
20520                         error "activate error"
20521                 }
20522         done
20523 }
20524 run_test 404 "validate manual {de}activated works properly for OSPs"
20525
20526 test_405() {
20527         [ -n "$FILESET" ] && skip "Not functional for FILESET set"
20528         [ $MDS1_VERSION -lt $(version_code 2.6.92) ] ||
20529                 [ $CLIENT_VERSION -lt $(version_code 2.6.99) ] &&
20530                         skip "Layout swap lock is not supported"
20531
20532         check_swap_layouts_support
20533
20534         test_mkdir $DIR/$tdir
20535         swap_lock_test -d $DIR/$tdir ||
20536                 error "One layout swap locked test failed"
20537 }
20538 run_test 405 "Various layout swap lock tests"
20539
20540 test_406() {
20541         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
20542         [ $OSTCOUNT -lt 2 ] && skip_env "needs >= 2 OSTs"
20543         [ -n "$FILESET" ] && skip "SKIP due to FILESET set"
20544         [ $PARALLEL == "yes" ] && skip "skip parallel run"
20545         [ $MDS1_VERSION -lt $(version_code 2.8.50) ] &&
20546                 skip "Need MDS version at least 2.8.50"
20547
20548         local def_stripe_size=$($LFS getstripe -S $MOUNT)
20549         local test_pool=$TESTNAME
20550
20551         pool_add $test_pool || error "pool_add failed"
20552         pool_add_targets $test_pool 0 $(($OSTCOUNT - 1)) 1 ||
20553                 error "pool_add_targets failed"
20554
20555         save_layout_restore_at_exit $MOUNT
20556
20557         # parent set default stripe count only, child will stripe from both
20558         # parent and fs default
20559         $LFS setstripe -c 1 -i 1 -S $((def_stripe_size * 2)) -p $test_pool $MOUNT ||
20560                 error "setstripe $MOUNT failed"
20561         $LFS mkdir -c $MDSCOUNT $DIR/$tdir || error "mkdir $tdir failed"
20562         $LFS setstripe -c $OSTCOUNT $DIR/$tdir || error "setstripe $tdir failed"
20563         for i in $(seq 10); do
20564                 local f=$DIR/$tdir/$tfile.$i
20565                 touch $f || error "touch failed"
20566                 local count=$($LFS getstripe -c $f)
20567                 [ $count -eq $OSTCOUNT ] ||
20568                         error "$f stripe count $count != $OSTCOUNT"
20569                 local offset=$($LFS getstripe -i $f)
20570                 [ $offset -eq 1 ] || error "$f stripe offset $offset != 1"
20571                 local size=$($LFS getstripe -S $f)
20572                 [ $size -eq $((def_stripe_size * 2)) ] ||
20573                         error "$f stripe size $size != $((def_stripe_size * 2))"
20574                 local pool=$($LFS getstripe -p $f)
20575                 [ $pool == $test_pool ] || error "$f pool $pool != $test_pool"
20576         done
20577
20578         # change fs default striping, delete parent default striping, now child
20579         # will stripe from new fs default striping only
20580         $LFS setstripe -c 1 -S $def_stripe_size -i 0 $MOUNT ||
20581                 error "change $MOUNT default stripe failed"
20582         $LFS setstripe -c 0 $DIR/$tdir ||
20583                 error "delete $tdir default stripe failed"
20584         for i in $(seq 11 20); do
20585                 local f=$DIR/$tdir/$tfile.$i
20586                 touch $f || error "touch $f failed"
20587                 local count=$($LFS getstripe -c $f)
20588                 [ $count -eq 1 ] || error "$f stripe count $count != 1"
20589                 local offset=$($LFS getstripe -i $f)
20590                 [ $offset -eq 0 ] || error "$f stripe offset $offset != 0"
20591                 local size=$($LFS getstripe -S $f)
20592                 [ $size -eq $def_stripe_size ] ||
20593                         error "$f stripe size $size != $def_stripe_size"
20594                 local pool=$($LFS getstripe -p $f)
20595                 [ $pool == $test_pool ] || error "$f pool $pool isn't set"
20596         done
20597
20598         unlinkmany $DIR/$tdir/$tfile. 1 20
20599
20600         local f=$DIR/$tdir/$tfile
20601         pool_remove_all_targets $test_pool $f
20602         pool_remove $test_pool $f
20603 }
20604 run_test 406 "DNE support fs default striping"
20605
20606 test_407() {
20607         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
20608         [[ $MDS1_VERSION -lt $(version_code 2.8.55) ]] &&
20609                 skip "Need MDS version at least 2.8.55"
20610         remote_mds_nodsh && skip "remote MDS with nodsh"
20611
20612         $LFS mkdir -i 0 -c 1 $DIR/$tdir.0 ||
20613                 error "$LFS mkdir -i 0 -c 1 $tdir.0 failed"
20614         $LFS mkdir -i 1 -c 1 $DIR/$tdir.1 ||
20615                 error "$LFS mkdir -i 1 -c 1 $tdir.1 failed"
20616         touch $DIR/$tdir.0/$tfile.0 || error "touch $tdir.0/$tfile.0 failed"
20617
20618         #define OBD_FAIL_DT_TXN_STOP    0x2019
20619         for idx in $(seq $MDSCOUNT); do
20620                 do_facet mds$idx "lctl set_param fail_loc=0x2019"
20621         done
20622         $LFS mkdir -c 2 $DIR/$tdir && error "$LFS mkdir -c 2 $tdir should fail"
20623         mv $DIR/$tdir.0/$tfile.0 $DIR/$tdir.1/$tfile.1 &&
20624                 error "mv $tdir.0/$tfile.0 $tdir.1/$tfile.1 should fail"
20625         true
20626 }
20627 run_test 407 "transaction fail should cause operation fail"
20628
20629 test_408() {
20630         dd if=/dev/zero of=$DIR/$tfile bs=$PAGE_SIZE count=1 oflag=direct
20631
20632         #define OBD_FAIL_OSC_BRW_PREP_REQ2        0x40a
20633         lctl set_param fail_loc=0x8000040a
20634         # let ll_prepare_partial_page() fail
20635         dd if=/dev/zero of=$DIR/$tfile bs=2048 count=1 conv=notrunc || true
20636
20637         rm -f $DIR/$tfile
20638
20639         # create at least 100 unused inodes so that
20640         # shrink_icache_memory(0) should not return 0
20641         touch $DIR/$tfile-{0..100}
20642         rm -f $DIR/$tfile-{0..100}
20643         sync
20644
20645         echo 2 > /proc/sys/vm/drop_caches
20646 }
20647 run_test 408 "drop_caches should not hang due to page leaks"
20648
20649 test_409()
20650 {
20651         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs"
20652
20653         mkdir -p $DIR/$tdir || error "(0) Fail to mkdir"
20654         $LFS mkdir -i 1 -c 2 $DIR/$tdir/foo || error "(1) Fail to mkdir"
20655         touch $DIR/$tdir/guard || error "(2) Fail to create"
20656
20657         local PREFIX=$(str_repeat 'A' 128)
20658         echo "Create 1K hard links start at $(date)"
20659         createmany -l $DIR/$tdir/guard $DIR/$tdir/foo/${PREFIX}_ 1000 ||
20660                 error "(3) Fail to hard link"
20661
20662         echo "Links count should be right although linkEA overflow"
20663         stat $DIR/$tdir/guard || error "(4) Fail to stat"
20664         local linkcount=$(stat --format=%h $DIR/$tdir/guard)
20665         [ $linkcount -eq 1001 ] ||
20666                 error "(5) Unexpected hard links count: $linkcount"
20667
20668         echo "List all links start at $(date)"
20669         ls -l $DIR/$tdir/foo > /dev/null ||
20670                 error "(6) Fail to list $DIR/$tdir/foo"
20671
20672         echo "Unlink hard links start at $(date)"
20673         unlinkmany $DIR/$tdir/foo/${PREFIX}_ 1000 ||
20674                 error "(7) Fail to unlink"
20675         echo "Unlink hard links finished at $(date)"
20676 }
20677 run_test 409 "Large amount of cross-MDTs hard links on the same file"
20678
20679 test_410()
20680 {
20681         [[ $CLIENT_VERSION -lt $(version_code 2.9.59) ]] &&
20682                 skip "Need client version at least 2.9.59"
20683
20684         # Create a file, and stat it from the kernel
20685         local testfile=$DIR/$tfile
20686         touch $testfile
20687
20688         local run_id=$RANDOM
20689         local my_ino=$(stat --format "%i" $testfile)
20690
20691         # Try to insert the module. This will always fail as the
20692         # module is designed to not be inserted.
20693         insmod $LUSTRE/tests/kernel/kinode.ko run_id=$run_id fname=$testfile \
20694             &> /dev/null
20695
20696         # Anything but success is a test failure
20697         dmesg | grep -q \
20698             "lustre_kinode_$run_id: inode numbers are identical: $my_ino" ||
20699             error "no inode match"
20700 }
20701 run_test 410 "Test inode number returned from kernel thread"
20702
20703 cleanup_test411_cgroup() {
20704         trap 0
20705         rmdir "$1"
20706 }
20707
20708 test_411() {
20709         local cg_basedir=/sys/fs/cgroup/memory
20710         # LU-9966
20711         test -f "$cg_basedir/memory.kmem.limit_in_bytes" ||
20712                 skip "no setup for cgroup"
20713
20714         dd if=/dev/zero of=$DIR/$tfile bs=1M count=100 conv=fsync ||
20715                 error "test file creation failed"
20716         cancel_lru_locks osc
20717
20718         # Create a very small memory cgroup to force a slab allocation error
20719         local cgdir=$cg_basedir/osc_slab_alloc
20720         mkdir $cgdir || error "cgroup mkdir '$cgdir' failed"
20721         trap "cleanup_test411_cgroup $cgdir" EXIT
20722         echo 2M > $cgdir/memory.kmem.limit_in_bytes
20723         echo 1M > $cgdir/memory.limit_in_bytes
20724
20725         # Should not LBUG, just be killed by oom-killer
20726         # dd will return 0 even allocation failure in some environment.
20727         # So don't check return value
20728         sh -c "echo \$$ > $cgdir/tasks && dd if=$DIR/$tfile of=/dev/null"
20729         cleanup_test411_cgroup $cgdir
20730
20731         return 0
20732 }
20733 run_test 411 "Slab allocation error with cgroup does not LBUG"
20734
20735 test_412() {
20736         [ $MDSCOUNT -lt 2 ] && skip_env "needs >= 2 MDTs"
20737         if [ $(lustre_version_code mds1) -lt $(version_code 2.10.55) ]; then
20738                 skip "Need server version at least 2.10.55"
20739         fi
20740
20741         $LFS mkdir -i $((MDSCOUNT - 1)),$((MDSCOUNT - 2)) $DIR/$tdir ||
20742                 error "mkdir failed"
20743         $LFS getdirstripe $DIR/$tdir
20744         local stripe_index=$($LFS getdirstripe -i $DIR/$tdir)
20745         [ $stripe_index -eq $((MDSCOUNT - 1)) ] ||
20746                 error "expect $((MDSCOUT - 1)) get $stripe_index"
20747         local stripe_count=$($LFS getdirstripe -T $DIR/$tdir)
20748         [ $stripe_count -eq 2 ] ||
20749                 error "expect 2 get $stripe_count"
20750 }
20751 run_test 412 "mkdir on specific MDTs"
20752
20753 test_qos_mkdir() {
20754         local mkdir_cmd=$1
20755         local stripe_count=$2
20756         local mdts=$(comma_list $(mdts_nodes))
20757
20758         local testdir
20759         local lmv_qos_prio_free
20760         local lmv_qos_threshold_rr
20761         local lmv_qos_maxage
20762         local lod_qos_prio_free
20763         local lod_qos_threshold_rr
20764         local lod_qos_maxage
20765         local count
20766         local i
20767
20768         lmv_qos_prio_free=$($LCTL get_param -n lmv.*.qos_prio_free | head -n1)
20769         lmv_qos_prio_free=${lmv_qos_prio_free%%%}
20770         lmv_qos_threshold_rr=$($LCTL get_param -n lmv.*.qos_threshold_rr |
20771                 head -n1)
20772         lmv_qos_threshold_rr=${lmv_qos_threshold_rr%%%}
20773         lmv_qos_maxage=$($LCTL get_param -n lmv.*.qos_maxage)
20774         stack_trap "$LCTL set_param \
20775                 lmv.*.qos_prio_free=$lmv_qos_prio_free > /dev/null" EXIT
20776         stack_trap "$LCTL set_param \
20777                 lmv.*.qos_threshold_rr=$lmv_qos_threshold_rr > /dev/null" EXIT
20778         stack_trap "$LCTL set_param \
20779                 lmv.*.qos_maxage=$lmv_qos_maxage > /dev/null" EXIT
20780
20781         lod_qos_prio_free=$(do_facet mds1 $LCTL get_param -n \
20782                 lod.lustre-MDT0000-mdtlov.mdt_qos_prio_free | head -n1)
20783         lod_qos_prio_free=${lod_qos_prio_free%%%}
20784         lod_qos_threshold_rr=$(do_facet mds1 $LCTL get_param -n \
20785                 lod.lustre-MDT0000-mdtlov.mdt_qos_thresholdrr | head -n1)
20786         lod_qos_threshold_rr=${lod_qos_threshold_rr%%%}
20787         lod_qos_maxage=$(do_facet mds1 $LCTL get_param -n \
20788                 lod.lustre-MDT0000-mdtlov.qos_maxage | awk '{ print $1 }')
20789         stack_trap "do_nodes $mdts $LCTL set_param \
20790                 lod.*.mdt_qos_prio_free=$lod_qos_prio_free > /dev/null" EXIT
20791         stack_trap "do_nodes $mdts $LCTL set_param \
20792                 lod.*.mdt_qos_thresholdrr=$lod_qos_threshold_rr > /dev/null" \
20793                 EXIT
20794         stack_trap "do_nodes $mdts $LCTL set_param \
20795                 lod.*.mdt_qos_maxage=$lod_qos_maxage > /dev/null" EXIT
20796
20797         echo
20798         echo "Mkdir (stripe_count $stripe_count) roundrobin:"
20799
20800         $LCTL set_param lmv.*.qos_threshold_rr=100 > /dev/null
20801         do_nodes $mdts $LCTL set_param lod.*.mdt_qos_thresholdrr=100 > /dev/null
20802
20803         testdir=$DIR/$tdir-s$stripe_count/rr
20804
20805         for i in $(seq $((100 * MDSCOUNT))); do
20806                 eval $mkdir_cmd $testdir/subdir$i ||
20807                         error "$mkdir_cmd subdir$i failed"
20808         done
20809
20810         for i in $(seq $MDSCOUNT); do
20811                 count=$($LFS getdirstripe -i $testdir/* |
20812                                 grep ^$((i - 1))$ | wc -l)
20813                 echo "$count directories created on MDT$((i - 1))"
20814                 [ $count -eq 100 ] || error "subdirs are not evenly distributed"
20815
20816                 if [ $stripe_count -gt 1 ]; then
20817                         count=$($LFS getdirstripe $testdir/* |
20818                                 grep -P "^\s+$((i - 1))\t" | wc -l)
20819                         echo "$count stripes created on MDT$((i - 1))"
20820                         # deviation should < 5% of average
20821                         [ $count -lt $((95 * stripe_count)) ] ||
20822                         [ $count -gt $((105 * stripe_count)) ] &&
20823                                 error "stripes are not evenly distributed"
20824                 fi
20825         done
20826
20827         $LCTL set_param lmv.*.qos_threshold_rr=$lmv_qos_threshold_rr > /dev/null
20828         do_nodes $mdts $LCTL set_param \
20829                 lod.*.mdt_qos_thresholdrr=$lod_qos_threshold_rr > /dev/null
20830
20831         echo
20832         echo "Check for uneven MDTs: "
20833
20834         local ffree
20835         local bavail
20836         local max
20837         local min
20838         local max_index
20839         local min_index
20840         local tmp
20841
20842         ffree=($(lctl get_param -n mdc.*[mM][dD][cC]-[^M]*.filesfree))
20843         bavail=($(lctl get_param -n mdc.*[mM][dD][cC]-[^M]*.kbytesavail))
20844         bsize=$(lctl get_param -n mdc.*MDT0000*.blocksize)
20845
20846         max=$(((${ffree[0]} >> 8) * (${bavail[0]} * bsize >> 16)))
20847         min=$(((${ffree[0]} >> 8) * (${bavail[0]} * bsize >> 16)))
20848         max_index=0
20849         min_index=0
20850         for ((i = 1; i < ${#ffree[@]}; i++)); do
20851                 tmp=$(((${ffree[i]} >> 8) * (${bavail[i]} * bsize >> 16)))
20852                 if [ $tmp -gt $max ]; then
20853                         max=$tmp
20854                         max_index=$i
20855                 fi
20856                 if [ $tmp -lt $min ]; then
20857                         min=$tmp
20858                         min_index=$i
20859                 fi
20860         done
20861
20862         [ ${ffree[min_index]} -eq 0 ] &&
20863                 skip "no free files in MDT$min_index"
20864         [ ${ffree[min_index]} -gt 100000000 ] &&
20865                 skip "too much free files in MDT$min_index"
20866
20867         # Check if we need to generate uneven MDTs
20868         local threshold=50
20869         local diff=$(((max - min) * 100 / min))
20870         local value="$(generate_string 1024)"
20871
20872         while [ $diff -lt $threshold ]; do
20873                 # generate uneven MDTs, create till $threshold% diff
20874                 echo -n "weight diff=$diff% must be > $threshold% ..."
20875                 count=$((${ffree[min_index]} / 10))
20876                 # 50 sec per 10000 files in vm
20877                 [ $count -gt 40000 ] && [ "$SLOW" = "no" ] &&
20878                         skip "$count files to create"
20879                 echo "Fill MDT$min_index with $count files"
20880                 [ -d $DIR/$tdir-MDT$min_index ] ||
20881                         $LFS mkdir -i $min_index $DIR/$tdir-MDT$min_index ||
20882                         error "mkdir $tdir-MDT$min_index failed"
20883                 for i in $(seq $count); do
20884                         $OPENFILE -f O_CREAT:O_LOV_DELAY_CREATE \
20885                                 $DIR/$tdir-MDT$min_index/f$j_$i > /dev/null ||
20886                                 error "create f$j_$i failed"
20887                         setfattr -n user.413b -v $value \
20888                                 $DIR/$tdir-MDT$min_index/f$j_$i ||
20889                                 error "setfattr f$j_$i failed"
20890                 done
20891
20892                 ffree=($(lctl get_param -n mdc.*[mM][dD][cC]-*.filesfree))
20893                 bavail=($(lctl get_param -n mdc.*[mM][dD][cC]-*.kbytesavail))
20894                 max=$(((${ffree[max_index]} >> 8) * \
20895                         (${bavail[max_index]} * bsize >> 16)))
20896                 min=$(((${ffree[min_index]} >> 8) * \
20897                         (${bavail[min_index]} * bsize >> 16)))
20898                 diff=$(((max - min) * 100 / min))
20899         done
20900
20901         echo "MDT filesfree available: ${ffree[@]}"
20902         echo "MDT blocks available: ${bavail[@]}"
20903         echo "weight diff=$diff%"
20904
20905         echo
20906         echo "Mkdir (stripe_count $stripe_count) with balanced space usage:"
20907
20908         $LCTL set_param lmv.*.qos_prio_free=100 > /dev/null
20909         do_nodes $mdts $LCTL set_param lod.*.mdt_qos_prio_free=100 > /dev/null
20910         # decrease statfs age, so that it can be updated in time
20911         $LCTL set_param lmv.*.qos_maxage=1 > /dev/null
20912         do_nodes $mdts $LCTL set_param lod.*.mdt_qos_maxage=1 > /dev/null
20913
20914         sleep 1
20915
20916         testdir=$DIR/$tdir-s$stripe_count/qos
20917
20918         for i in $(seq $((100 * MDSCOUNT))); do
20919                 eval $mkdir_cmd $testdir/subdir$i ||
20920                         error "$mkdir_cmd subdir$i failed"
20921         done
20922
20923         for i in $(seq $MDSCOUNT); do
20924                 count=$($LFS getdirstripe -i $testdir/* | grep ^$((i - 1))$ |
20925                         wc -l)
20926                 echo "$count directories created on MDT$((i - 1))"
20927
20928                 if [ $stripe_count -gt 1 ]; then
20929                         count=$($LFS getdirstripe $testdir/* |
20930                                 grep -P "^\s+$((i - 1))\t" | wc -l)
20931                         echo "$count stripes created on MDT$((i - 1))"
20932                 fi
20933         done
20934
20935         max=$($LFS getdirstripe -i $testdir/* | grep ^$max_index$ | wc -l)
20936         min=$($LFS getdirstripe -i $testdir/* | grep ^$min_index$ | wc -l)
20937
20938         # D-value should > 10% of averge
20939         [ $((max - min)) -lt 10 ] &&
20940                 error "subdirs shouldn't be evenly distributed"
20941
20942         # ditto
20943         if [ $stripe_count -gt 1 ]; then
20944                 max=$($LFS getdirstripe $testdir/* |
20945                         grep -P "^\s+$max_index\t" | wc -l)
20946                 min=$($LFS getdirstripe $testdir/* |
20947                         grep -P "^\s+$min_index\t" | wc -l)
20948                 [ $((max - min)) -le $((10 * stripe_count)) ] &&
20949                         error "stripes shouldn't be evenly distributed"|| true
20950         fi
20951 }
20952
20953 test_413a() {
20954         [ $MDSCOUNT -lt 2 ] &&
20955                 skip "We need at least 2 MDTs for this test"
20956
20957         [ $MDS1_VERSION -lt $(version_code 2.12.52) ] &&
20958                 skip "Need server version at least 2.12.52"
20959
20960         local stripe_count
20961
20962         for stripe_count in $(seq 1 $((MDSCOUNT - 1))); do
20963                 mkdir $DIR/$tdir-s$stripe_count || error "mkdir failed"
20964                 mkdir $DIR/$tdir-s$stripe_count/rr || error "mkdir failed"
20965                 mkdir $DIR/$tdir-s$stripe_count/qos || error "mkdir failed"
20966                 test_qos_mkdir "$LFS mkdir -c $stripe_count" $stripe_count
20967         done
20968 }
20969 run_test 413a "QoS mkdir with 'lfs mkdir -i -1'"
20970
20971 test_413b() {
20972         [ $MDSCOUNT -lt 2 ] &&
20973                 skip "We need at least 2 MDTs for this test"
20974
20975         [ $MDS1_VERSION -lt $(version_code 2.12.52) ] &&
20976                 skip "Need server version at least 2.12.52"
20977
20978         local stripe_count
20979
20980         for stripe_count in $(seq 1 $((MDSCOUNT - 1))); do
20981                 mkdir $DIR/$tdir-s$stripe_count || error "mkdir failed"
20982                 mkdir $DIR/$tdir-s$stripe_count/rr || error "mkdir failed"
20983                 mkdir $DIR/$tdir-s$stripe_count/qos || error "mkdir failed"
20984                 $LFS setdirstripe -D -c $stripe_count \
20985                         $DIR/$tdir-s$stripe_count/rr ||
20986                         error "setdirstripe failed"
20987                 $LFS setdirstripe -D -c $stripe_count \
20988                         $DIR/$tdir-s$stripe_count/qos ||
20989                         error "setdirstripe failed"
20990                 test_qos_mkdir "mkdir" $stripe_count
20991         done
20992 }
20993 run_test 413b "QoS mkdir under dir whose default LMV starting MDT offset is -1"
20994
20995 test_414() {
20996 #define OBD_FAIL_PTLRPC_BULK_ATTACH      0x521
20997         $LCTL set_param fail_loc=0x80000521
20998         dd if=/dev/zero of=$DIR/$tfile bs=2M count=1 oflag=sync
20999         rm -f $DIR/$tfile
21000 }
21001 run_test 414 "simulate ENOMEM in ptlrpc_register_bulk()"
21002
21003 test_415() {
21004         [ $PARALLEL == "yes" ] && skip "skip parallel run"
21005         [ $(lustre_version_code mds1) -lt $(version_code 2.11.52) ] &&
21006                 skip "Need server version at least 2.11.52"
21007
21008         # LU-11102
21009         local total
21010         local setattr_pid
21011         local start_time
21012         local end_time
21013         local duration
21014
21015         total=500
21016         # this test may be slow on ZFS
21017         [ "$mds1_FSTYPE" == "zfs" ] && total=100
21018
21019         # though this test is designed for striped directory, let's test normal
21020         # directory too since lock is always saved as CoS lock.
21021         test_mkdir $DIR/$tdir || error "mkdir $tdir"
21022         createmany -o $DIR/$tdir/$tfile. $total || error "createmany"
21023
21024         (
21025                 while true; do
21026                         touch $DIR/$tdir
21027                 done
21028         ) &
21029         setattr_pid=$!
21030
21031         start_time=$(date +%s)
21032         for i in $(seq $total); do
21033                 mrename $DIR/$tdir/$tfile.$i $DIR/$tdir/$tfile-new.$i \
21034                         > /dev/null
21035         done
21036         end_time=$(date +%s)
21037         duration=$((end_time - start_time))
21038
21039         kill -9 $setattr_pid
21040
21041         echo "rename $total files took $duration sec"
21042         [ $duration -lt 100 ] || error "rename took $duration sec"
21043 }
21044 run_test 415 "lock revoke is not missing"
21045
21046 test_416() {
21047         [ $(lustre_version_code mds1) -lt $(version_code 2.11.55) ] &&
21048                 skip "Need server version at least 2.11.55"
21049
21050         # define OBD_FAIL_OSD_TXN_START    0x19a
21051         do_facet mds1 lctl set_param fail_loc=0x19a
21052
21053         lfs mkdir -c $MDSCOUNT $DIR/$tdir
21054
21055         true
21056 }
21057 run_test 416 "transaction start failure won't cause system hung"
21058
21059 cleanup_417() {
21060         trap 0
21061         do_nodes $(comma_list $(mdts_nodes)) \
21062                 "$LCTL set_param -n mdt.*MDT*.enable_dir_migration=1"
21063         do_nodes $(comma_list $(mdts_nodes)) \
21064                 "$LCTL set_param -n mdt.*MDT*.enable_remote_dir=1"
21065         do_nodes $(comma_list $(mdts_nodes)) \
21066                 "$LCTL set_param -n mdt.*MDT*.enable_striped_dir=1"
21067 }
21068
21069 test_417() {
21070         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs"
21071         [[ $MDS1_VERSION -lt $(version_code 2.11.56) ]] &&
21072                 skip "Need MDS version at least 2.11.56"
21073
21074         trap cleanup_417 RETURN EXIT
21075
21076         $LFS mkdir -i 1 $DIR/$tdir.1 || error "create remote dir $tdir.1 failed"
21077         do_nodes $(comma_list $(mdts_nodes)) \
21078                 "$LCTL set_param -n mdt.*MDT*.enable_dir_migration=0"
21079         $LFS migrate -m 0 $DIR/$tdir.1 &&
21080                 error "migrate dir $tdir.1 should fail"
21081
21082         do_nodes $(comma_list $(mdts_nodes)) \
21083                 "$LCTL set_param -n mdt.*MDT*.enable_remote_dir=0"
21084         $LFS mkdir -i 1 $DIR/$tdir.2 &&
21085                 error "create remote dir $tdir.2 should fail"
21086
21087         do_nodes $(comma_list $(mdts_nodes)) \
21088                 "$LCTL set_param -n mdt.*MDT*.enable_striped_dir=0"
21089         $LFS mkdir -c 2 $DIR/$tdir.3 &&
21090                 error "create striped dir $tdir.3 should fail"
21091         true
21092 }
21093 run_test 417 "disable remote dir, striped dir and dir migration"
21094
21095 # Checks that the outputs of df [-i] and lfs df [-i] match
21096 #
21097 # usage: check_lfs_df <blocks | inodes> <mountpoint>
21098 check_lfs_df() {
21099         local dir=$2
21100         local inodes
21101         local df_out
21102         local lfs_df_out
21103         local count
21104         local passed=false
21105
21106         # blocks or inodes
21107         [ "$1" == "blocks" ] && inodes= || inodes="-i"
21108
21109         for count in {1..100}; do
21110                 cancel_lru_locks
21111                 sync; sleep 0.2
21112
21113                 # read the lines of interest
21114                 df_out=($(df -P $inodes $dir | tail -n +2)) ||
21115                         error "df $inodes $dir | tail -n +2 failed"
21116                 lfs_df_out=($($LFS df $inodes $dir | grep summary:)) ||
21117                         error "lfs df $inodes $dir | grep summary: failed"
21118
21119                 # skip first substrings of each output as they are different
21120                 # "<NID>:/<fsname>" for df, "filesystem_summary:" for lfs df
21121                 # compare the two outputs
21122                 passed=true
21123                 for i in {1..5}; do
21124                         [ "${df_out[i]}" != "${lfs_df_out[i]}" ] && passed=false
21125                 done
21126                 $passed && break
21127         done
21128
21129         if ! $passed; then
21130                 df -P $inodes $dir
21131                 echo
21132                 lfs df $inodes $dir
21133                 error "df and lfs df $1 output mismatch: "      \
21134                       "df ${inodes}: ${df_out[*]}, "            \
21135                       "lfs df ${inodes}: ${lfs_df_out[*]}"
21136         fi
21137 }
21138
21139 test_418() {
21140         [ $PARALLEL == "yes" ] && skip "skip parallel run"
21141
21142         local dir=$DIR/$tdir
21143         local numfiles=$((RANDOM % 4096 + 2))
21144         local numblocks=$((RANDOM % 256 + 1))
21145
21146         wait_delete_completed
21147         test_mkdir $dir
21148
21149         # check block output
21150         check_lfs_df blocks $dir
21151         # check inode output
21152         check_lfs_df inodes $dir
21153
21154         # create a single file and retest
21155         echo "Creating a single file and testing"
21156         createmany -o $dir/$tfile- 1 &>/dev/null ||
21157                 error "creating 1 file in $dir failed"
21158         check_lfs_df blocks $dir
21159         check_lfs_df inodes $dir
21160
21161         # create a random number of files
21162         echo "Creating $((numfiles - 1)) files and testing"
21163         createmany -o $dir/$tfile- 1 $((numfiles - 1)) &>/dev/null ||
21164                 error "creating $((numfiles - 1)) files in $dir failed"
21165
21166         # write a random number of blocks to the first test file
21167         echo "Writing $numblocks 4K blocks and testing"
21168         dd if=/dev/urandom of=$dir/${tfile}-0 bs=4K conv=fsync \
21169                 count=$numblocks &>/dev/null ||
21170                 error "dd to $dir/${tfile}-0 failed"
21171
21172         # retest
21173         check_lfs_df blocks $dir
21174         check_lfs_df inodes $dir
21175
21176         unlinkmany $dir/$tfile- $numfiles &>/dev/null ||
21177                 error "unlinking $numfiles files in $dir failed"
21178 }
21179 run_test 418 "df and lfs df outputs match"
21180
21181 test_419()
21182 {
21183         local dir=$DIR/$tdir
21184
21185         mkdir -p $dir
21186         touch $dir/file
21187
21188         cancel_lru_locks mdc
21189
21190         #OBD_FAIL_LLITE_OPEN_BY_NAME    0x1410
21191         $LCTL set_param fail_loc=0x1410
21192         cat $dir/file
21193         $LCTL set_param fail_loc=0
21194         rm -rf $dir
21195 }
21196 run_test 419 "Verify open file by name doesn't crash kernel"
21197
21198 test_420()
21199 {
21200         [[ $MDS1_VERSION -ge $(version_code 2.12.53) ]] ||
21201                 skip "Need MDS version at least 2.12.53"
21202
21203         local SAVE_UMASK=$(umask)
21204         local dir=$DIR/$tdir
21205         local uname=$(getent passwd $RUNAS_ID | cut -d: -f1)
21206
21207         mkdir -p $dir
21208         umask 0000
21209         mkdir -m03777 $dir/testdir
21210         ls -dn $dir/testdir
21211         # Need to remove trailing '.' when SELinux is enabled
21212         local dirperms=$(ls -dn $dir/testdir |
21213                          awk '{ sub(/\.$/, "", $1); print $1}')
21214         [ $dirperms == "drwxrwsrwt" ] ||
21215                 error "incorrect perms on $dir/testdir"
21216
21217         su - $uname -c "PATH=$LUSTRE/tests:\$PATH; \
21218                 openfile -f O_RDONLY:O_CREAT -m 02755 $dir/testdir/testfile"
21219         ls -n $dir/testdir/testfile
21220         local fileperms=$(ls -n $dir/testdir/testfile |
21221                           awk '{ sub(/\.$/, "", $1); print $1}')
21222         [ $fileperms == "-rwxr-xr-x" ] ||
21223                 error "incorrect perms on $dir/testdir/testfile"
21224
21225         umask $SAVE_UMASK
21226 }
21227 run_test 420 "clear SGID bit on non-directories for non-members"
21228
21229 test_421a() {
21230         local cnt
21231         local fid1
21232         local fid2
21233
21234         [ $MDS1_VERSION -lt $(version_code 2.12.54) ] &&
21235                 skip "Need MDS version at least 2.12.54"
21236
21237         test_mkdir $DIR/$tdir
21238         createmany -o $DIR/$tdir/f 3
21239         cnt=$(ls -1 $DIR/$tdir | wc -l)
21240         [ $cnt != 3 ] && error "unexpected #files: $cnt"
21241
21242         fid1=$(lfs path2fid $DIR/$tdir/f1)
21243         fid2=$(lfs path2fid $DIR/$tdir/f2)
21244         $LFS rmfid $DIR $fid1 $fid2 || error "rmfid failed"
21245
21246         stat $DIR/$tdir/f1 && error "f1 still visible on the client"
21247         stat $DIR/$tdir/f2 && error "f2 still visible on the client"
21248
21249         cnt=$(ls -1 $DIR/$tdir | wc -l)
21250         [ $cnt == 1 ] || error "unexpected #files after: $cnt"
21251
21252         rm -f $DIR/$tdir/f3 || error "can't remove f3"
21253         createmany -o $DIR/$tdir/f 3
21254         cnt=$(ls -1 $DIR/$tdir | wc -l)
21255         [ $cnt != 3 ] && error "unexpected #files: $cnt"
21256
21257         fid1=$(lfs path2fid $DIR/$tdir/f1)
21258         fid2=$(lfs path2fid $DIR/$tdir/f2)
21259         echo "remove using fsname $FSNAME"
21260         $LFS rmfid $FSNAME $fid1 $fid2 || error "rmfid with fsname failed"
21261
21262         cnt=$(ls -1 $DIR/$tdir | wc -l)
21263         [ $cnt == 1 ] || error "unexpected #files after: $cnt"
21264 }
21265 run_test 421a "simple rm by fid"
21266
21267 test_421b() {
21268         local cnt
21269         local FID1
21270         local FID2
21271
21272         [ $MDS1_VERSION -lt $(version_code 2.12.54) ] &&
21273                 skip "Need MDS version at least 2.12.54"
21274
21275         test_mkdir $DIR/$tdir
21276         createmany -o $DIR/$tdir/f 3
21277         multiop_bg_pause $DIR/$tdir/f1 o_c || error "multiop failed to start"
21278         MULTIPID=$!
21279
21280         FID1=$(lfs path2fid $DIR/$tdir/f1)
21281         FID2=$(lfs path2fid $DIR/$tdir/f2)
21282         $LFS rmfid $DIR $FID1 $FID2 && error "rmfid didn't fail"
21283
21284         kill -USR1 $MULTIPID
21285         wait
21286
21287         cnt=$(ls $DIR/$tdir | wc -l)
21288         [ $cnt == 2 ] || error "unexpected #files after: $cnt"
21289 }
21290 run_test 421b "rm by fid on open file"
21291
21292 test_421c() {
21293         local cnt
21294         local FIDS
21295
21296         [ $MDS1_VERSION -lt $(version_code 2.12.54) ] &&
21297                 skip "Need MDS version at least 2.12.54"
21298
21299         test_mkdir $DIR/$tdir
21300         createmany -o $DIR/$tdir/f 3
21301         touch $DIR/$tdir/$tfile
21302         createmany -l$DIR/$tdir/$tfile $DIR/$tdir/h 180
21303         cnt=$(ls -1 $DIR/$tdir | wc -l)
21304         [ $cnt != 184 ] && error "unexpected #files: $cnt"
21305
21306         FID1=$(lfs path2fid $DIR/$tdir/$tfile)
21307         $LFS rmfid $DIR $FID1 || error "rmfid failed"
21308
21309         cnt=$(ls $DIR/$tdir | wc -l)
21310         [ $cnt == 3 ] || error "unexpected #files after: $cnt"
21311 }
21312 run_test 421c "rm by fid against hardlinked files"
21313
21314 test_421d() {
21315         local cnt
21316         local FIDS
21317
21318         [ $MDS1_VERSION -lt $(version_code 2.12.54) ] &&
21319                 skip "Need MDS version at least 2.12.54"
21320
21321         test_mkdir $DIR/$tdir
21322         createmany -o $DIR/$tdir/f 4097
21323         cnt=$(ls -1 $DIR/$tdir | wc -l)
21324         [ $cnt != 4097 ] && error "unexpected #files: $cnt"
21325
21326         FIDS=$(lfs path2fid $DIR/$tdir/f* | sed "s/[/][^:]*://g")
21327         $LFS rmfid $DIR $FIDS || error "rmfid failed"
21328
21329         cnt=$(ls $DIR/$tdir | wc -l)
21330         rm -rf $DIR/$tdir
21331         [ $cnt == 0 ] || error "unexpected #files after: $cnt"
21332 }
21333 run_test 421d "rmfid en masse"
21334
21335 test_421e() {
21336         local cnt
21337         local FID
21338
21339         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs"
21340         [ $MDS1_VERSION -lt $(version_code 2.12.54) ] &&
21341                 skip "Need MDS version at least 2.12.54"
21342
21343         mkdir -p $DIR/$tdir
21344         $LFS setdirstripe -c$MDSCOUNT $DIR/$tdir/striped_dir
21345         createmany -o $DIR/$tdir/striped_dir/f 512
21346         cnt=$(ls -1 $DIR/$tdir/striped_dir | wc -l)
21347         [ $cnt != 512 ] && error "unexpected #files: $cnt"
21348
21349         FIDS=$(lfs path2fid $DIR/$tdir/striped_dir/f* |
21350                 sed "s/[/][^:]*://g")
21351         $LFS rmfid $DIR $FIDS || error "rmfid failed"
21352
21353         cnt=$(ls $DIR/$tdir/striped_dir | wc -l)
21354         rm -rf $DIR/$tdir
21355         [ $cnt == 0 ] || error "unexpected #files after: $cnt"
21356 }
21357 run_test 421e "rmfid in DNE"
21358
21359 test_421f() {
21360         local cnt
21361         local FID
21362
21363         [ $MDS1_VERSION -lt $(version_code 2.12.54) ] &&
21364                 skip "Need MDS version at least 2.12.54"
21365
21366         test_mkdir $DIR/$tdir
21367         touch $DIR/$tdir/f
21368         cnt=$(ls -1 $DIR/$tdir | wc -l)
21369         [ $cnt != 1 ] && error "unexpected #files: $cnt"
21370
21371         FID=$(lfs path2fid $DIR/$tdir/f)
21372         $RUNAS $LFS rmfid $DIR $FID && error "rmfid didn't fail (1)"
21373         # rmfid should fail
21374         cnt=$(ls -1 $DIR/$tdir | wc -l)
21375         [ $cnt != 1 ] && error "unexpected #files after (2): $cnt"
21376
21377         chmod a+rw $DIR/$tdir
21378         ls -la $DIR/$tdir
21379         $RUNAS $LFS rmfid $DIR $FID && error "rmfid didn't fail (2)"
21380         # rmfid should fail
21381         cnt=$(ls -1 $DIR/$tdir | wc -l)
21382         [ $cnt != 1 ] && error "unexpected #files after (3): $cnt"
21383
21384         rm -f $DIR/$tdir/f
21385         $RUNAS touch $DIR/$tdir/f
21386         FID=$(lfs path2fid $DIR/$tdir/f)
21387         echo "rmfid as root"
21388         $LFS rmfid $DIR $FID || error "rmfid as root failed"
21389         cnt=$(ls -1 $DIR/$tdir | wc -l)
21390         [ $cnt == 0 ] || error "unexpected #files after (4): $cnt"
21391
21392         rm -f $DIR/$tdir/f
21393         $RUNAS touch $DIR/$tdir/f
21394         cnt=$(ls -1 $DIR/$tdir | wc -l)
21395         [ $cnt != 1 ] && error "unexpected #files (4): $cnt"
21396         FID=$(lfs path2fid $DIR/$tdir/f)
21397         # rmfid w/o user_fid2path mount option should fail
21398         $RUNAS $LFS rmfid $DIR $FID && error "rmfid didn't fail(3)"
21399         cnt=$(ls -1 $DIR/$tdir | wc -l)
21400         [ $cnt == 1 ] || error "unexpected #files after (5): $cnt"
21401
21402         umount_client $MOUNT || error "failed to umount client"
21403         mount_client $MOUNT "$MOUNT_OPTS,user_fid2path" ||
21404                 error "failed to mount client'"
21405
21406         $RUNAS $LFS rmfid $DIR $FID || error "rmfid failed"
21407         # rmfid should succeed
21408         cnt=$(ls -1 $DIR/$tdir | wc -l)
21409         [ $cnt == 0 ] || error "unexpected #files after (6): $cnt"
21410
21411         # rmfid shouldn't allow to remove files due to dir's permission
21412         chmod a+rwx $DIR/$tdir
21413         touch $DIR/$tdir/f
21414         ls -la $DIR/$tdir
21415         FID=$(lfs path2fid $DIR/$tdir/f)
21416         $RUNAS $LFS rmfid $DIR $FID && error "rmfid didn't fail"
21417
21418         umount_client $MOUNT || error "failed to umount client"
21419         mount_client $MOUNT "$MOUNT_OPTS" ||
21420                 error "failed to mount client'"
21421
21422 }
21423 run_test 421f "rmfid checks permissions"
21424
21425 test_421g() {
21426         local cnt
21427         local FIDS
21428
21429         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs"
21430         [ $MDS1_VERSION -lt $(version_code 2.12.54) ] &&
21431                 skip "Need MDS version at least 2.12.54"
21432
21433         mkdir -p $DIR/$tdir
21434         $LFS setdirstripe -c$MDSCOUNT $DIR/$tdir/striped_dir
21435         createmany -o $DIR/$tdir/striped_dir/f 512
21436         cnt=$(ls -1 $DIR/$tdir/striped_dir | wc -l)
21437         [ $cnt != 512 ] && error "unexpected #files: $cnt"
21438
21439         FIDS=$(lfs path2fid $DIR/$tdir/striped_dir/f* |
21440                 sed "s/[/][^:]*://g")
21441
21442         rm -f $DIR/$tdir/striped_dir/f1*
21443         cnt=$(ls -1 $DIR/$tdir/striped_dir | wc -l)
21444         removed=$((512 - cnt))
21445
21446         # few files have been just removed, so we expect
21447         # rmfid to fail on their fids
21448         errors=$($LFS rmfid $DIR $FIDS 2>&1 | wc -l)
21449         [ $removed != $errors ] && error "$errors != $removed"
21450
21451         cnt=$(ls $DIR/$tdir/striped_dir | wc -l)
21452         rm -rf $DIR/$tdir
21453         [ $cnt == 0 ] || error "unexpected #files after: $cnt"
21454 }
21455 run_test 421g "rmfid to return errors properly"
21456
21457 test_422() {
21458         test_mkdir -i 0 -c 1 -p $DIR/$tdir/d1
21459         test_mkdir -i 0 -c 1 -p $DIR/$tdir/d2
21460         test_mkdir -i 0 -c 1 -p $DIR/$tdir/d3
21461         dd if=/dev/zero of=$DIR/$tdir/d1/file1 bs=1k count=1
21462         dd if=/dev/zero of=$DIR/$tdir/d2/file1 bs=1k count=1
21463
21464         local amc=$(at_max_get client)
21465         local amo=$(at_max_get mds1)
21466         local timeout=`lctl get_param -n timeout`
21467
21468         at_max_set 0 client
21469         at_max_set 0 mds1
21470
21471 #define OBD_FAIL_PTLRPC_PAUSE_REQ        0x50a
21472         do_facet mds1 $LCTL set_param fail_loc=0x8000050a \
21473                         fail_val=$(((2*timeout + 10)*1000))
21474         touch $DIR/$tdir/d3/file &
21475         sleep 2
21476 #define OBD_FAIL_TGT_REPLY_DATA_RACE     0x722
21477         do_facet mds1 $LCTL set_param fail_loc=0x80000722 \
21478                         fail_val=$((2*timeout + 5))
21479         mv $DIR/$tdir/d1/file1 $DIR/$tdir/d1/file2 &
21480         local pid=$!
21481         sleep 1
21482         kill -9 $pid
21483         sleep $((2 * timeout))
21484         echo kill $pid
21485         kill -9 $pid
21486         lctl mark touch
21487         touch $DIR/$tdir/d2/file3
21488         touch $DIR/$tdir/d2/file4
21489         touch $DIR/$tdir/d2/file5
21490
21491         wait
21492         at_max_set $amc client
21493         at_max_set $amo mds1
21494
21495         # LU-12838 - verify the ptlrpc thread watchdog is not always throttled
21496         do_facet mds1 "dmesg | grep 'Dumping the stack trace for debugging'" ||
21497                 error "Watchdog is always throttled"
21498 }
21499 run_test 422 "kill a process with RPC in progress"
21500
21501 prep_801() {
21502         [[ $(lustre_version_code mds1) -lt $(version_code 2.9.55) ]] ||
21503         [[ $OST1_VERSION -lt $(version_code 2.9.55) ]] &&
21504                 skip "Need server version at least 2.9.55"
21505
21506         start_full_debug_logging
21507 }
21508
21509 post_801() {
21510         stop_full_debug_logging
21511 }
21512
21513 barrier_stat() {
21514         if [ $MGS_VERSION -le $(version_code 2.10.0) ]; then
21515                 local st=$(do_facet mgs $LCTL barrier_stat $FSNAME |
21516                            awk '/The barrier for/ { print $7 }')
21517                 echo $st
21518         else
21519                 local st=$(do_facet mgs $LCTL barrier_stat -s $FSNAME)
21520                 echo \'$st\'
21521         fi
21522 }
21523
21524 barrier_expired() {
21525         local expired
21526
21527         if [ $MGS_VERSION -le $(version_code 2.10.0) ]; then
21528                 expired=$(do_facet mgs $LCTL barrier_stat $FSNAME |
21529                           awk '/will be expired/ { print $7 }')
21530         else
21531                 expired=$(do_facet mgs $LCTL barrier_stat -t $FSNAME)
21532         fi
21533
21534         echo $expired
21535 }
21536
21537 test_801a() {
21538         prep_801
21539
21540         echo "Start barrier_freeze at: $(date)"
21541         #define OBD_FAIL_BARRIER_DELAY          0x2202
21542         do_facet mgs $LCTL set_param fail_val=5 fail_loc=0x2202
21543         # Do not reduce barrier time - See LU-11873
21544         do_facet mgs $LCTL barrier_freeze $FSNAME 20 &
21545
21546         sleep 2
21547         local b_status=$(barrier_stat)
21548         echo "Got barrier status at: $(date)"
21549         [ "$b_status" = "'freezing_p1'" ] ||
21550                 error "(1) unexpected barrier status $b_status"
21551
21552         do_facet mgs $LCTL set_param fail_val=0 fail_loc=0
21553         wait
21554         b_status=$(barrier_stat)
21555         [ "$b_status" = "'frozen'" ] ||
21556                 error "(2) unexpected barrier status $b_status"
21557
21558         local expired=$(barrier_expired)
21559         echo "sleep $((expired + 3)) seconds, then the barrier will be expired"
21560         sleep $((expired + 3))
21561
21562         b_status=$(barrier_stat)
21563         [ "$b_status" = "'expired'" ] ||
21564                 error "(3) unexpected barrier status $b_status"
21565
21566         # Do not reduce barrier time - See LU-11873
21567         do_facet mgs $LCTL barrier_freeze $FSNAME 20 ||
21568                 error "(4) fail to freeze barrier"
21569
21570         b_status=$(barrier_stat)
21571         [ "$b_status" = "'frozen'" ] ||
21572                 error "(5) unexpected barrier status $b_status"
21573
21574         echo "Start barrier_thaw at: $(date)"
21575         #define OBD_FAIL_BARRIER_DELAY          0x2202
21576         do_facet mgs $LCTL set_param fail_val=5 fail_loc=0x2202
21577         do_facet mgs $LCTL barrier_thaw $FSNAME &
21578
21579         sleep 2
21580         b_status=$(barrier_stat)
21581         echo "Got barrier status at: $(date)"
21582         [ "$b_status" = "'thawing'" ] ||
21583                 error "(6) unexpected barrier status $b_status"
21584
21585         do_facet mgs $LCTL set_param fail_val=0 fail_loc=0
21586         wait
21587         b_status=$(barrier_stat)
21588         [ "$b_status" = "'thawed'" ] ||
21589                 error "(7) unexpected barrier status $b_status"
21590
21591         #define OBD_FAIL_BARRIER_FAILURE        0x2203
21592         do_facet $SINGLEMDS $LCTL set_param fail_loc=0x2203
21593         do_facet mgs $LCTL barrier_freeze $FSNAME
21594
21595         b_status=$(barrier_stat)
21596         [ "$b_status" = "'failed'" ] ||
21597                 error "(8) unexpected barrier status $b_status"
21598
21599         do_facet $SINGLEMDS $LCTL set_param fail_loc=0
21600         do_facet mgs $LCTL barrier_thaw $FSNAME
21601
21602         post_801
21603 }
21604 run_test 801a "write barrier user interfaces and stat machine"
21605
21606 test_801b() {
21607         prep_801
21608
21609         mkdir $DIR/$tdir || error "(1) fail to mkdir"
21610         createmany -d $DIR/$tdir/d 6 || "(2) fail to mkdir"
21611         touch $DIR/$tdir/d2/f10 || error "(3) fail to touch"
21612         touch $DIR/$tdir/d3/f11 || error "(4) fail to touch"
21613         touch $DIR/$tdir/d4/f12 || error "(5) fail to touch"
21614
21615         cancel_lru_locks mdc
21616
21617         # 180 seconds should be long enough
21618         do_facet mgs $LCTL barrier_freeze $FSNAME 180
21619
21620         local b_status=$(barrier_stat)
21621         [ "$b_status" = "'frozen'" ] ||
21622                 error "(6) unexpected barrier status $b_status"
21623
21624         mkdir $DIR/$tdir/d0/d10 &
21625         mkdir_pid=$!
21626
21627         touch $DIR/$tdir/d1/f13 &
21628         touch_pid=$!
21629
21630         ln $DIR/$tdir/d2/f10 $DIR/$tdir/d2/f14 &
21631         ln_pid=$!
21632
21633         mv $DIR/$tdir/d3/f11 $DIR/$tdir/d3/f15 &
21634         mv_pid=$!
21635
21636         rm -f $DIR/$tdir/d4/f12 &
21637         rm_pid=$!
21638
21639         stat $DIR/$tdir/d5 || error "(7) stat should succeed"
21640
21641         # To guarantee taht the 'stat' is not blocked
21642         b_status=$(barrier_stat)
21643         [ "$b_status" = "'frozen'" ] ||
21644                 error "(8) unexpected barrier status $b_status"
21645
21646         # let above commands to run at background
21647         sleep 5
21648
21649         ps -p $mkdir_pid || error "(9) mkdir should be blocked"
21650         ps -p $touch_pid || error "(10) touch should be blocked"
21651         ps -p $ln_pid || error "(11) link should be blocked"
21652         ps -p $mv_pid || error "(12) rename should be blocked"
21653         ps -p $rm_pid || error "(13) unlink should be blocked"
21654
21655         b_status=$(barrier_stat)
21656         [ "$b_status" = "'frozen'" ] ||
21657                 error "(14) unexpected barrier status $b_status"
21658
21659         do_facet mgs $LCTL barrier_thaw $FSNAME
21660         b_status=$(barrier_stat)
21661         [ "$b_status" = "'thawed'" ] ||
21662                 error "(15) unexpected barrier status $b_status"
21663
21664         wait $mkdir_pid || error "(16) mkdir should succeed"
21665         wait $touch_pid || error "(17) touch should succeed"
21666         wait $ln_pid || error "(18) link should succeed"
21667         wait $mv_pid || error "(19) rename should succeed"
21668         wait $rm_pid || error "(20) unlink should succeed"
21669
21670         post_801
21671 }
21672 run_test 801b "modification will be blocked by write barrier"
21673
21674 test_801c() {
21675         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 2 MDTs"
21676
21677         prep_801
21678
21679         stop mds2 || error "(1) Fail to stop mds2"
21680
21681         do_facet mgs $LCTL barrier_freeze $FSNAME 30
21682
21683         local b_status=$(barrier_stat)
21684         [ "$b_status" = "'expired'" ] || [ "$b_status" = "'failed'" ] || {
21685                 do_facet mgs $LCTL barrier_thaw $FSNAME
21686                 error "(2) unexpected barrier status $b_status"
21687         }
21688
21689         do_facet mgs $LCTL barrier_rescan $FSNAME ||
21690                 error "(3) Fail to rescan barrier bitmap"
21691
21692         # Do not reduce barrier time - See LU-11873
21693         do_facet mgs $LCTL barrier_freeze $FSNAME 20
21694
21695         b_status=$(barrier_stat)
21696         [ "$b_status" = "'frozen'" ] ||
21697                 error "(4) unexpected barrier status $b_status"
21698
21699         do_facet mgs $LCTL barrier_thaw $FSNAME
21700         b_status=$(barrier_stat)
21701         [ "$b_status" = "'thawed'" ] ||
21702                 error "(5) unexpected barrier status $b_status"
21703
21704         local devname=$(mdsdevname 2)
21705
21706         start mds2 $devname $MDS_MOUNT_OPTS || error "(6) Fail to start mds2"
21707
21708         do_facet mgs $LCTL barrier_rescan $FSNAME ||
21709                 error "(7) Fail to rescan barrier bitmap"
21710
21711         post_801
21712 }
21713 run_test 801c "rescan barrier bitmap"
21714
21715 saved_MGS_MOUNT_OPTS=$MGS_MOUNT_OPTS
21716 saved_MDS_MOUNT_OPTS=$MDS_MOUNT_OPTS
21717 saved_OST_MOUNT_OPTS=$OST_MOUNT_OPTS
21718 saved_MOUNT_OPTS=$MOUNT_OPTS
21719
21720 cleanup_802a() {
21721         trap 0
21722
21723         stopall
21724         MGS_MOUNT_OPTS=$saved_MGS_MOUNT_OPTS
21725         MDS_MOUNT_OPTS=$saved_MDS_MOUNT_OPTS
21726         OST_MOUNT_OPTS=$saved_OST_MOUNT_OPTS
21727         MOUNT_OPTS=$saved_MOUNT_OPTS
21728         setupall
21729 }
21730
21731 test_802a() {
21732         [[ $mds1_FSTYPE = zfs ]] || skip "ZFS specific test"
21733         [[ $(lustre_version_code mds1) -lt $(version_code 2.9.55) ]] ||
21734         [[ $OST1_VERSION -lt $(version_code 2.9.55) ]] &&
21735                 skip "Need server version at least 2.9.55"
21736
21737         [[ $ENABLE_QUOTA ]] && skip "Quota enabled for read-only test"
21738
21739         mkdir $DIR/$tdir || error "(1) fail to mkdir"
21740
21741         cp $LUSTRE/tests/test-framework.sh $DIR/$tdir/ ||
21742                 error "(2) Fail to copy"
21743
21744         trap cleanup_802a EXIT
21745
21746         # sync by force before remount as readonly
21747         sync; sync_all_data; sleep 3; sync_all_data
21748
21749         stopall
21750
21751         MGS_MOUNT_OPTS=$(csa_add "$MGS_MOUNT_OPTS" -o rdonly_dev)
21752         MDS_MOUNT_OPTS=$(csa_add "$MDS_MOUNT_OPTS" -o rdonly_dev)
21753         OST_MOUNT_OPTS=$(csa_add "$OST_MOUNT_OPTS" -o rdonly_dev)
21754
21755         echo "Mount the server as read only"
21756         setupall server_only || error "(3) Fail to start servers"
21757
21758         echo "Mount client without ro should fail"
21759         mount_client $MOUNT &&
21760                 error "(4) Mount client without 'ro' should fail"
21761
21762         echo "Mount client with ro should succeed"
21763         MOUNT_OPTS=$(csa_add "$MOUNT_OPTS" -o ro)
21764         mount_client $MOUNT ||
21765                 error "(5) Mount client with 'ro' should succeed"
21766
21767         echo "Modify should be refused"
21768         touch $DIR/$tdir/guard && error "(6) Touch should fail under ro mode"
21769
21770         echo "Read should be allowed"
21771         diff $LUSTRE/tests/test-framework.sh $DIR/$tdir/test-framework.sh ||
21772                 error "(7) Read should succeed under ro mode"
21773
21774         cleanup_802a
21775 }
21776 run_test 802a "simulate readonly device"
21777
21778 test_802b() {
21779         [ $PARALLEL == "yes" ] && skip "skip parallel run"
21780         remote_mds_nodsh && skip "remote MDS with nodsh"
21781
21782         do_facet $SINGLEMDS $LCTL get_param mdt.*.readonly ||
21783                 skip "readonly option not available"
21784
21785         $LFS mkdir -i 0 -c 1 $DIR/$tdir || error "(1) fail to mkdir"
21786
21787         cp $LUSTRE/tests/test-framework.sh $DIR/$tdir/ ||
21788                 error "(2) Fail to copy"
21789
21790         # write back all cached data before setting MDT to readonly
21791         cancel_lru_locks
21792         sync_all_data
21793
21794         do_facet $SINGLEMDS $LCTL set_param mdt.*.readonly=1
21795         stack_trap "do_facet $SINGLEMDS $LCTL set_param mdt.*.readonly=0" EXIT
21796
21797         echo "Modify should be refused"
21798         touch $DIR/$tdir/guard && error "(6) Touch should fail under ro mode"
21799
21800         echo "Read should be allowed"
21801         diff $LUSTRE/tests/test-framework.sh $DIR/$tdir/test-framework.sh ||
21802                 error "(7) Read should succeed under ro mode"
21803
21804         # disable readonly
21805         do_facet $SINGLEMDS $LCTL set_param mdt.*.readonly=0
21806 }
21807 run_test 802b "be able to set MDTs to readonly"
21808
21809 test_803() {
21810         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 2 MDTs"
21811         [ $MDS1_VERSION -lt $(version_code 2.10.54) ] &&
21812                 skip "MDS needs to be newer than 2.10.54"
21813
21814         mkdir -p $DIR/$tdir
21815         # Create some objects on all MDTs to trigger related logs objects
21816         for idx in $(seq $MDSCOUNT); do
21817                 $LFS mkdir -c $MDSCOUNT -i $((idx % $MDSCOUNT)) \
21818                         $DIR/$tdir/dir${idx} ||
21819                         error "Fail to create $DIR/$tdir/dir${idx}"
21820         done
21821
21822         sync; sleep 3
21823         wait_delete_completed # ensure old test cleanups are finished
21824         echo "before create:"
21825         $LFS df -i $MOUNT
21826         local before_used=$($LFS df -i | grep MDT0000_UUID | awk '{print $3}')
21827
21828         for i in {1..10}; do
21829                 $LFS mkdir -c 1 -i 1 $DIR/$tdir/foo$i ||
21830                         error "Fail to create $DIR/$tdir/foo$i"
21831         done
21832
21833         sync; sleep 3
21834         echo "after create:"
21835         $LFS df -i $MOUNT
21836         local after_used=$($LFS df -i | grep MDT0000_UUID | awk '{print $3}')
21837
21838         # allow for an llog to be cleaned up during the test
21839         [ $after_used -ge $((before_used + 10 - 1)) ] ||
21840                 error "before ($before_used) + 10 > after ($after_used)"
21841
21842         for i in {1..10}; do
21843                 rm -rf $DIR/$tdir/foo$i ||
21844                         error "Fail to remove $DIR/$tdir/foo$i"
21845         done
21846
21847         sleep 3 # avoid MDT return cached statfs
21848         wait_delete_completed
21849         echo "after unlink:"
21850         $LFS df -i $MOUNT
21851         after_used=$($LFS df -i | grep MDT0000_UUID | awk '{print $3}')
21852
21853         # allow for an llog to be created during the test
21854         [ $after_used -le $((before_used + 1)) ] ||
21855                 error "after ($after_used) > before ($before_used) + 1"
21856 }
21857 run_test 803 "verify agent object for remote object"
21858
21859 test_804() {
21860         [[ $MDSCOUNT -lt 2 ]] && skip_env "needs >= 2 MDTs"
21861         [ $MDS1_VERSION -lt $(version_code 2.10.54) ] &&
21862                 skip "MDS needs to be newer than 2.10.54"
21863         [ "$mds1_FSTYPE" != "ldiskfs" ] && skip_env "ldiskfs only test"
21864
21865         mkdir -p $DIR/$tdir
21866         $LFS mkdir -c 1 -i 1 $DIR/$tdir/dir0 ||
21867                 error "Fail to create $DIR/$tdir/dir0"
21868
21869         local fid=$($LFS path2fid $DIR/$tdir/dir0)
21870         local dev=$(mdsdevname 2)
21871
21872         do_facet mds2 "$DEBUGFS -c -R 'ls /REMOTE_PARENT_DIR' $dev" |
21873                 grep ${fid} || error "NOT found agent entry for dir0"
21874
21875         $LFS mkdir -c $MDSCOUNT -i 0 $DIR/$tdir/dir1 ||
21876                 error "Fail to create $DIR/$tdir/dir1"
21877
21878         touch $DIR/$tdir/dir1/foo0 ||
21879                 error "Fail to create $DIR/$tdir/dir1/foo0"
21880         fid=$($LFS path2fid $DIR/$tdir/dir1/foo0)
21881         local rc=0
21882
21883         for idx in $(seq $MDSCOUNT); do
21884                 dev=$(mdsdevname $idx)
21885                 do_facet mds${idx} \
21886                         "$DEBUGFS -c -R 'ls /REMOTE_PARENT_DIR' $dev" |
21887                         grep ${fid} && rc=$idx
21888         done
21889
21890         mv $DIR/$tdir/dir1/foo0 $DIR/$tdir/dir1/foo1 ||
21891                 error "Fail to rename foo0 to foo1"
21892         if [ $rc -eq 0 ]; then
21893                 for idx in $(seq $MDSCOUNT); do
21894                         dev=$(mdsdevname $idx)
21895                         do_facet mds${idx} \
21896                         "$DEBUGFS -c -R 'ls /REMOTE_PARENT_DIR' $dev" |
21897                         grep ${fid} && rc=$idx
21898                 done
21899         fi
21900
21901         mv $DIR/$tdir/dir1/foo1 $DIR/$tdir/dir1/foo2 ||
21902                 error "Fail to rename foo1 to foo2"
21903         if [ $rc -eq 0 ]; then
21904                 for idx in $(seq $MDSCOUNT); do
21905                         dev=$(mdsdevname $idx)
21906                         do_facet mds${idx} \
21907                         "$DEBUGFS -c -R 'ls /REMOTE_PARENT_DIR' $dev" |
21908                         grep ${fid} && rc=$idx
21909                 done
21910         fi
21911
21912         [ $rc -ne 0 ] || error "NOT found agent entry for foo"
21913
21914         ln $DIR/$tdir/dir1/foo2 $DIR/$tdir/dir0/guard ||
21915                 error "Fail to link to $DIR/$tdir/dir1/foo2"
21916         mv $DIR/$tdir/dir1/foo2 $DIR/$tdir/dir1/foo0 ||
21917                 error "Fail to rename foo2 to foo0"
21918         unlink $DIR/$tdir/dir1/foo0 ||
21919                 error "Fail to unlink $DIR/$tdir/dir1/foo0"
21920         rm -rf $DIR/$tdir/dir0 ||
21921                 error "Fail to rm $DIR/$tdir/dir0"
21922
21923         for idx in $(seq $MDSCOUNT); do
21924                 dev=$(mdsdevname $idx)
21925                 rc=0
21926
21927                 stop mds${idx}
21928                 run_e2fsck $(facet_active_host mds$idx) $dev -n ||
21929                         rc=$?
21930                 start mds${idx} $dev $MDS_MOUNT_OPTS ||
21931                         error "mount mds$idx failed"
21932                 df $MOUNT > /dev/null 2>&1
21933
21934                 # e2fsck should not return error
21935                 [ $rc -eq 0 ] ||
21936                         error "e2fsck detected error on MDT${idx}: rc=$rc"
21937         done
21938 }
21939 run_test 804 "verify agent entry for remote entry"
21940
21941 cleanup_805() {
21942         do_facet $SINGLEMDS zfs set quota=$old $fsset
21943         unlinkmany $DIR/$tdir/f- 1000000
21944         trap 0
21945 }
21946
21947 test_805() {
21948         local zfs_version=$(do_facet mds1 cat /sys/module/zfs/version)
21949         [ "$mds1_FSTYPE" != "zfs" ] && skip "ZFS specific test"
21950         [ $(version_code $zfs_version) -lt $(version_code 0.7.2) ] &&
21951                 skip "netfree not implemented before 0.7"
21952         [[ $MDS1_VERSION -ge $(version_code 2.10.57) ]] ||
21953                 skip "Need MDS version at least 2.10.57"
21954
21955         local fsset
21956         local freekb
21957         local usedkb
21958         local old
21959         local quota
21960         local pref="osd-zfs.lustre-MDT0000."
21961
21962         # limit available space on MDS dataset to meet nospace issue
21963         # quickly. then ZFS 0.7.2 can use reserved space if asked
21964         # properly (using netfree flag in osd_declare_destroy()
21965         fsset=$(do_facet $SINGLEMDS lctl get_param -n $pref.mntdev)
21966         old=$(do_facet $SINGLEMDS zfs get -H quota $fsset | \
21967                 gawk '{print $3}')
21968         freekb=$(do_facet $SINGLEMDS lctl get_param -n $pref.kbytesfree)
21969         usedkb=$(do_facet $SINGLEMDS lctl get_param -n $pref.kbytestotal)
21970         let "usedkb=usedkb-freekb"
21971         let "freekb=freekb/2"
21972         if let "freekb > 5000"; then
21973                 let "freekb=5000"
21974         fi
21975         do_facet $SINGLEMDS zfs set quota=$(((usedkb+freekb)*1024)) $fsset
21976         trap cleanup_805 EXIT
21977         mkdir $DIR/$tdir
21978         $LFS setstripe -E 1M -L mdt $DIR/$tdir || error "DoM not working"
21979         createmany -m $DIR/$tdir/f- 1000000 && error "ENOSPC wasn't met"
21980         rm -rf $DIR/$tdir || error "not able to remove"
21981         do_facet $SINGLEMDS zfs set quota=$old $fsset
21982         trap 0
21983 }
21984 run_test 805 "ZFS can remove from full fs"
21985
21986 # Size-on-MDS test
21987 check_lsom_data()
21988 {
21989         local file=$1
21990         local size=$($LFS getsom -s $file)
21991         local expect=$(stat -c %s $file)
21992
21993         [[ $size == $expect ]] ||
21994                 error "$file expected size: $expect, got: $size"
21995
21996         local blocks=$($LFS getsom -b $file)
21997         expect=$(stat -c %b $file)
21998         [[ $blocks == $expect ]] ||
21999                 error "$file expected blocks: $expect, got: $blocks"
22000 }
22001
22002 check_lsom_size()
22003 {
22004         local size=$($LFS getsom -s $1)
22005         local expect=$2
22006
22007         [[ $size == $expect ]] ||
22008                 error "$file expected size: $expect, got: $size"
22009 }
22010
22011 test_806() {
22012         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
22013                 skip "Need MDS version at least 2.11.52"
22014
22015         local bs=1048576
22016
22017         touch $DIR/$tfile || error "touch $tfile failed"
22018
22019         local save="$TMP/$TESTSUITE-$TESTNAME.parameters"
22020         save_lustre_params client "llite.*.xattr_cache" > $save
22021         lctl set_param llite.*.xattr_cache=0
22022         stack_trap "restore_lustre_params < $save; rm -f $save" EXIT
22023
22024         # single-threaded write
22025         echo "Test SOM for single-threaded write"
22026         dd if=/dev/zero of=$DIR/$tfile bs=$bs count=1 ||
22027                 error "write $tfile failed"
22028         check_lsom_size $DIR/$tfile $bs
22029
22030         local num=32
22031         local size=$(($num * $bs))
22032         local offset=0
22033         local i
22034
22035         echo "Test SOM for single client multi-threaded($num) write"
22036         $TRUNCATE $DIR/$tfile 0
22037         for ((i = 0; i < $num; i++)); do
22038                 $MULTIOP $DIR/$tfile Oz${offset}w${bs}c &
22039                 local pids[$i]=$!
22040                 offset=$((offset + $bs))
22041         done
22042         for (( i=0; i < $num; i++ )); do
22043                 wait ${pids[$i]}
22044         done
22045         check_lsom_size $DIR/$tfile $size
22046
22047         $TRUNCATE $DIR/$tfile 0
22048         for ((i = 0; i < $num; i++)); do
22049                 offset=$((offset - $bs))
22050                 $MULTIOP $DIR/$tfile Oz${offset}w${bs}c &
22051                 local pids[$i]=$!
22052         done
22053         for (( i=0; i < $num; i++ )); do
22054                 wait ${pids[$i]}
22055         done
22056         check_lsom_size $DIR/$tfile $size
22057
22058         # multi-client writes
22059         num=$(get_node_count ${CLIENTS//,/ })
22060         size=$(($num * $bs))
22061         offset=0
22062         i=0
22063
22064         echo "Test SOM for multi-client ($num) writes"
22065         $TRUNCATE $DIR/$tfile 0
22066         for client in ${CLIENTS//,/ }; do
22067                 do_node $client $MULTIOP $DIR/$tfile Oz${offset}w${bs}c &
22068                 local pids[$i]=$!
22069                 i=$((i + 1))
22070                 offset=$((offset + $bs))
22071         done
22072         for (( i=0; i < $num; i++ )); do
22073                 wait ${pids[$i]}
22074         done
22075         check_lsom_size $DIR/$tfile $offset
22076
22077         i=0
22078         $TRUNCATE $DIR/$tfile 0
22079         for client in ${CLIENTS//,/ }; do
22080                 offset=$((offset - $bs))
22081                 do_node $client $MULTIOP $DIR/$tfile Oz${offset}w${bs}c &
22082                 local pids[$i]=$!
22083                 i=$((i + 1))
22084         done
22085         for (( i=0; i < $num; i++ )); do
22086                 wait ${pids[$i]}
22087         done
22088         check_lsom_size $DIR/$tfile $size
22089
22090         # verify truncate
22091         echo "Test SOM for truncate"
22092         $TRUNCATE $DIR/$tfile 1048576
22093         check_lsom_size $DIR/$tfile 1048576
22094         $TRUNCATE $DIR/$tfile 1234
22095         check_lsom_size $DIR/$tfile 1234
22096
22097         # verify SOM blocks count
22098         echo "Verify SOM block count"
22099         $TRUNCATE $DIR/$tfile 0
22100         $MULTIOP $DIR/$tfile oO_TRUNC:O_RDWR:w1048576YSc ||
22101                 error "failed to write file $tfile"
22102         check_lsom_data $DIR/$tfile
22103 }
22104 run_test 806 "Verify Lazy Size on MDS"
22105
22106 test_807() {
22107         [ -n "$FILESET" ] && skip "Not functional for FILESET set"
22108         [ $MDS1_VERSION -lt $(version_code 2.11.52) ] &&
22109                 skip "Need MDS version at least 2.11.52"
22110
22111         # Registration step
22112         changelog_register || error "changelog_register failed"
22113         local cl_user="${CL_USERS[$SINGLEMDS]%% *}"
22114         changelog_users $SINGLEMDS | grep -q $cl_user ||
22115                 error "User $cl_user not found in changelog_users"
22116
22117         local save="$TMP/$TESTSUITE-$TESTNAME.parameters"
22118         save_lustre_params client "llite.*.xattr_cache" > $save
22119         lctl set_param llite.*.xattr_cache=0
22120         stack_trap "restore_lustre_params < $save; rm -f $save" EXIT
22121
22122         rm -rf $DIR/$tdir || error "rm $tdir failed"
22123         mkdir -p $DIR/$tdir || error "mkdir $tdir failed"
22124         touch $DIR/$tdir/trunc || error "touch $tdir/trunc failed"
22125         $TRUNCATE $DIR/$tdir/trunc 1024 || error "truncate $tdir/trunc failed"
22126         $TRUNCATE $DIR/$tdir/trunc 1048576 ||
22127                 error "truncate $tdir/trunc failed"
22128
22129         local bs=1048576
22130         dd if=/dev/zero of=$DIR/$tdir/single_dd bs=$bs count=1 ||
22131                 error "write $tfile failed"
22132
22133         # multi-client wirtes
22134         local num=$(get_node_count ${CLIENTS//,/ })
22135         local offset=0
22136         local i=0
22137
22138         echo "Test SOM for multi-client ($num) writes"
22139         touch $DIR/$tfile || error "touch $tfile failed"
22140         $TRUNCATE $DIR/$tfile 0
22141         for client in ${CLIENTS//,/ }; do
22142                 do_node $client $MULTIOP $DIR/$tfile Oz${offset}w${bs}c &
22143                 local pids[$i]=$!
22144                 i=$((i + 1))
22145                 offset=$((offset + $bs))
22146         done
22147         for (( i=0; i < $num; i++ )); do
22148                 wait ${pids[$i]}
22149         done
22150
22151         sleep 5
22152         $LSOM_SYNC -u $cl_user -m $FSNAME-MDT0000 $MOUNT
22153         check_lsom_data $DIR/$tdir/trunc
22154         check_lsom_data $DIR/$tdir/single_dd
22155         check_lsom_data $DIR/$tfile
22156
22157         rm -rf $DIR/$tdir
22158         # Deregistration step
22159         changelog_deregister || error "changelog_deregister failed"
22160 }
22161 run_test 807 "verify LSOM syncing tool"
22162
22163 check_som_nologged()
22164 {
22165         local lines=$($LFS changelog $FSNAME-MDT0000 |
22166                 grep 'x=trusted.som' | wc -l)
22167         [ $lines -ne 0 ] && error "trusted.som xattr is logged in Changelogs"
22168 }
22169
22170 test_808() {
22171         [ $MDS1_VERSION -lt $(version_code 2.11.55) ] &&
22172                 skip "Need MDS version at least 2.11.55"
22173
22174         # Registration step
22175         changelog_register || error "changelog_register failed"
22176
22177         touch $DIR/$tfile || error "touch $tfile failed"
22178         check_som_nologged
22179
22180         dd if=/dev/zero of=$DIR/$tfile bs=1048576 count=1 ||
22181                 error "write $tfile failed"
22182         check_som_nologged
22183
22184         $TRUNCATE $DIR/$tfile 1234
22185         check_som_nologged
22186
22187         $TRUNCATE $DIR/$tfile 1048576
22188         check_som_nologged
22189
22190         # Deregistration step
22191         changelog_deregister || error "changelog_deregister failed"
22192 }
22193 run_test 808 "Check trusted.som xattr not logged in Changelogs"
22194
22195 check_som_nodata()
22196 {
22197         $LFS getsom $1
22198         [[ $? -eq 61 ]] || error "DoM-only file $1 has SOM xattr"
22199 }
22200
22201 test_809() {
22202         [ $MDS1_VERSION -lt $(version_code 2.11.56) ] &&
22203                 skip "Need MDS version at least 2.11.56"
22204
22205         $LFS setstripe -E 1M -L mdt $DIR/$tfile ||
22206                 error "failed to create DoM-only file $DIR/$tfile"
22207         touch $DIR/$tfile || error "touch $tfile failed"
22208         check_som_nodata $DIR/$tfile
22209
22210         dd if=/dev/zero of=$DIR/$tfile bs=2048 count=1 ||
22211                 error "write $tfile failed"
22212         check_som_nodata $DIR/$tfile
22213
22214         $TRUNCATE $DIR/$tfile 1234
22215         check_som_nodata $DIR/$tfile
22216
22217         $TRUNCATE $DIR/$tfile 4097
22218         check_som_nodata $DIR/$file
22219 }
22220 run_test 809 "Verify no SOM xattr store for DoM-only files"
22221
22222 test_810() {
22223         [ $PARALLEL == "yes" ] && skip "skip parallel run"
22224         $GSS && skip_env "could not run with gss"
22225         [[ $OST1_VERSION -gt $(version_code 2.12.58) ]] ||
22226                 skip "OST < 2.12.58 doesn't align checksum"
22227
22228         set_checksums 1
22229         stack_trap "set_checksums $ORIG_CSUM" EXIT
22230         stack_trap "set_checksum_type $ORIG_CSUM_TYPE" EXIT
22231
22232         local csum
22233         local before
22234         local after
22235         for csum in $CKSUM_TYPES; do
22236                 #define OBD_FAIL_OSC_NO_GRANT   0x411
22237                 $LCTL set_param osc.*.checksum_type=$csum fail_loc=0x411
22238                 for i in "10240 0" "10000 0" "4000 1" "500 1"; do
22239                         eval set -- $i
22240                         dd if=/dev/urandom of=$DIR/$tfile bs=$1 count=2 seek=$2
22241                         before=$(md5sum $DIR/$tfile)
22242                         $LCTL set_param ldlm.namespaces.*osc*.lru_size=clear
22243                         after=$(md5sum $DIR/$tfile)
22244                         [ "$before" == "$after" ] ||
22245                                 error "$csum: $before != $after bs=$1 seek=$2"
22246                 done
22247         done
22248 }
22249 run_test 810 "partial page writes on ZFS (LU-11663)"
22250
22251 test_811() {
22252         [ $(lustre_version_code $SINGLEMDS) -lt $(version_code 2.11.56) ] &&
22253                 skip "Need MDS version at least 2.11.56"
22254
22255         #define OBD_FAIL_MDS_ORPHAN_DELETE      0x165
22256         do_facet mds1 $LCTL set_param fail_loc=0x165
22257         $MULTIOP $DIR/$tfile Ouc || error "multiop failed"
22258
22259         stop mds1
22260         start mds1 $(mdsdevname 1) $MDS_MOUNT_OPTS
22261
22262         sleep 5
22263         [[ $(do_facet mds1 pgrep orph_.*-MDD | wc -l) -eq 0 ]] ||
22264                 error "MDD orphan cleanup thread not quit"
22265 }
22266 run_test 811 "orphan name stub can be cleaned up in startup"
22267
22268 test_812() {
22269         [ $OST1_VERSION -lt $(version_code 2.12.51) ] &&
22270                 skip "OST < 2.12.51 doesn't support this fail_loc"
22271         [ "$SHARED_KEY" = true ] &&
22272                 skip "OSC connections never go IDLE with Shared-Keys enabled"
22273
22274         $LFS setstripe -c 1 -i 0 $DIR/$tfile
22275         # ensure ost1 is connected
22276         stat $DIR/$tfile >/dev/null || error "can't stat"
22277         wait_osc_import_state client ost1 FULL
22278         # no locks, no reqs to let the connection idle
22279         cancel_lru_locks osc
22280
22281         # delay OST_DISCONNECT on OST1 to put OSC into intermediate state
22282 #define OBD_FAIL_OST_DISCONNECT_DELAY    0x245
22283         do_facet ost1 "$LCTL set_param fail_loc=0x245 fail_val=8"
22284         wait_osc_import_state client ost1 CONNECTING
22285         do_facet ost1 "$LCTL set_param fail_loc=0 fail_val=0"
22286
22287         stat $DIR/$tfile >/dev/null || error "can't stat file"
22288 }
22289 run_test 812 "do not drop reqs generated when imp is going to idle (LU-11951)"
22290
22291 test_813() {
22292         local file_heat_sav=$($LCTL get_param -n llite.*.file_heat 2>/dev/null)
22293         [ -z "$file_heat_sav" ] && skip "no file heat support"
22294
22295         local readsample
22296         local writesample
22297         local readbyte
22298         local writebyte
22299         local readsample1
22300         local writesample1
22301         local readbyte1
22302         local writebyte1
22303
22304         local period_second=$($LCTL get_param -n llite.*.heat_period_second)
22305         local decay_pct=$($LCTL get_param -n llite.*.heat_decay_percentage)
22306
22307         $LCTL set_param -n llite.*.file_heat=1
22308         echo "Turn on file heat"
22309         echo "Period second: $period_second, Decay percentage: $decay_pct"
22310
22311         echo "QQQQ" > $DIR/$tfile
22312         echo "QQQQ" > $DIR/$tfile
22313         echo "QQQQ" > $DIR/$tfile
22314         cat $DIR/$tfile > /dev/null
22315         cat $DIR/$tfile > /dev/null
22316         cat $DIR/$tfile > /dev/null
22317         cat $DIR/$tfile > /dev/null
22318
22319         local out=$($LFS heat_get $DIR/$tfile)
22320
22321         $LFS heat_get $DIR/$tfile
22322         readsample=$(echo "$out" | grep 'readsample' | awk '{ print $2 }')
22323         writesample=$(echo "$out" | grep 'writesample' | awk '{ print $2 }')
22324         readbyte=$(echo "$out" | grep 'readbyte' | awk '{ print $2 }')
22325         writebyte=$(echo "$out" | grep 'writebyte' | awk '{ print $2 }')
22326
22327         [ $readsample -le 4 ] || error "read sample ($readsample) is wrong"
22328         [ $writesample -le 3 ] || error "write sample ($writesample) is wrong"
22329         [ $readbyte -le 20 ] || error "read bytes ($readbyte) is wrong"
22330         [ $writebyte -le 15 ] || error "write bytes ($writebyte) is wrong"
22331
22332         sleep $((period_second + 3))
22333         echo "Sleep $((period_second + 3)) seconds..."
22334         # The recursion formula to calculate the heat of the file f is as
22335         # follow:
22336         # Hi+1(f) = (1-P)*Hi(f)+ P*Ci
22337         # Where Hi is the heat value in the period between time points i*I and
22338         # (i+1)*I; Ci is the access count in the period; the symbol P refers
22339         # to the weight of Ci.
22340         out=$($LFS heat_get $DIR/$tfile)
22341         $LFS heat_get $DIR/$tfile
22342         readsample=$(echo "$out" | grep 'readsample' | awk '{ print $2 }')
22343         writesample=$(echo "$out" | grep 'writesample' | awk '{ print $2 }')
22344         readbyte=$(echo "$out" | grep 'readbyte' | awk '{ print $2 }')
22345         writebyte=$(echo "$out" | grep 'writebyte' | awk '{ print $2 }')
22346
22347         [ $(bc <<< "$readsample <= 4 * $decay_pct / 100") -eq 1 ] ||
22348                 error "read sample ($readsample) is wrong"
22349         [ $(bc <<< "$writesample <= 3 * $decay_pct / 100") -eq 1 ] ||
22350                 error "write sample ($writesample) is wrong"
22351         [ $(bc <<< "$readbyte <= 20 * $decay_pct / 100") -eq 1 ] ||
22352                 error "read bytes ($readbyte) is wrong"
22353         [ $(bc <<< "$writebyte <= 15 * $decay_pct / 100") -eq 1 ] ||
22354                 error "write bytes ($writebyte) is wrong"
22355
22356         echo "QQQQ" > $DIR/$tfile
22357         echo "QQQQ" > $DIR/$tfile
22358         echo "QQQQ" > $DIR/$tfile
22359         cat $DIR/$tfile > /dev/null
22360         cat $DIR/$tfile > /dev/null
22361         cat $DIR/$tfile > /dev/null
22362         cat $DIR/$tfile > /dev/null
22363
22364         sleep $((period_second + 3))
22365         echo "Sleep $((period_second + 3)) seconds..."
22366
22367         out=$($LFS heat_get $DIR/$tfile)
22368         $LFS heat_get $DIR/$tfile
22369         readsample1=$(echo "$out" | grep 'readsample' | awk '{ print $2 }')
22370         writesample1=$(echo "$out" | grep 'writesample' | awk '{ print $2 }')
22371         readbyte1=$(echo "$out" | grep 'readbyte' | awk '{ print $2 }')
22372         writebyte1=$(echo "$out" | grep 'writebyte' | awk '{ print $2 }')
22373
22374         [ $(bc <<< "$readsample1 <= ($readsample * (100 - $decay_pct) + \
22375                 4 * $decay_pct) / 100") -eq 1 ] ||
22376                 error "read sample ($readsample1) is wrong"
22377         [ $(bc <<< "$writesample1 <= ($writesample * (100 - $decay_pct) + \
22378                 3 * $decay_pct) / 100") -eq 1 ] ||
22379                 error "write sample ($writesample1) is wrong"
22380         [ $(bc <<< "$readbyte1 <= ($readbyte * (100 - $decay_pct) + \
22381                 20 * $decay_pct) / 100") -eq 1 ] ||
22382                 error "read bytes ($readbyte1) is wrong"
22383         [ $(bc <<< "$writebyte1 <= ($writebyte * (100 - $decay_pct) + \
22384                 15 * $decay_pct) / 100") -eq 1 ] ||
22385                 error "write bytes ($writebyte1) is wrong"
22386
22387         echo "Turn off file heat for the file $DIR/$tfile"
22388         $LFS heat_set -o $DIR/$tfile
22389
22390         echo "QQQQ" > $DIR/$tfile
22391         echo "QQQQ" > $DIR/$tfile
22392         echo "QQQQ" > $DIR/$tfile
22393         cat $DIR/$tfile > /dev/null
22394         cat $DIR/$tfile > /dev/null
22395         cat $DIR/$tfile > /dev/null
22396         cat $DIR/$tfile > /dev/null
22397
22398         out=$($LFS heat_get $DIR/$tfile)
22399         $LFS heat_get $DIR/$tfile
22400         readsample=$(echo "$out" | grep 'readsample' | awk '{ print $2 }')
22401         writesample=$(echo "$out" | grep 'writesample' | awk '{ print $2 }')
22402         readbyte=$(echo "$out" | grep 'readbyte' | awk '{ print $2 }')
22403         writebyte=$(echo "$out" | grep 'writebyte' | awk '{ print $2 }')
22404
22405         [ $readsample -eq 0 ] || error "read sample ($readsample) is wrong"
22406         [ $writesample -eq 0 ] || error "write sample ($writesample) is wrong"
22407         [ $readbyte -eq 0 ] || error "read bytes ($readbyte) is wrong"
22408         [ $writebyte -eq 0 ] || error "write bytes ($writebyte) is wrong"
22409
22410         echo "Trun on file heat for the file $DIR/$tfile"
22411         $LFS heat_set -O $DIR/$tfile
22412
22413         echo "QQQQ" > $DIR/$tfile
22414         echo "QQQQ" > $DIR/$tfile
22415         echo "QQQQ" > $DIR/$tfile
22416         cat $DIR/$tfile > /dev/null
22417         cat $DIR/$tfile > /dev/null
22418         cat $DIR/$tfile > /dev/null
22419         cat $DIR/$tfile > /dev/null
22420
22421         out=$($LFS heat_get $DIR/$tfile)
22422         $LFS heat_get $DIR/$tfile
22423         readsample=$(echo "$out" | grep 'readsample' | awk '{ print $2 }')
22424         writesample=$(echo "$out" | grep 'writesample' | awk '{ print $2 }')
22425         readbyte=$(echo "$out" | grep 'readbyte' | awk '{ print $2 }')
22426         writebyte=$(echo "$out" | grep 'writebyte' | awk '{ print $2 }')
22427
22428         [ $readsample -gt 0 ] || error "read sample ($readsample) is wrong"
22429         [ $writesample -gt 0 ] || error "write sample ($writesample) is wrong"
22430         [ $readbyte -gt 0 ] || error "read bytes ($readbyte) is wrong"
22431         [ $writebyte -gt 0 ] || error "write bytes ($writebyte) is wrong"
22432
22433         $LFS heat_set -c $DIR/$tfile
22434         $LCTL set_param -n llite.*.file_heat=0
22435         echo "Turn off file heat support for the Lustre filesystem"
22436
22437         echo "QQQQ" > $DIR/$tfile
22438         echo "QQQQ" > $DIR/$tfile
22439         echo "QQQQ" > $DIR/$tfile
22440         cat $DIR/$tfile > /dev/null
22441         cat $DIR/$tfile > /dev/null
22442         cat $DIR/$tfile > /dev/null
22443         cat $DIR/$tfile > /dev/null
22444
22445         out=$($LFS heat_get $DIR/$tfile)
22446         $LFS heat_get $DIR/$tfile
22447         readsample=$(echo "$out" | grep 'readsample' | awk '{ print $2 }')
22448         writesample=$(echo "$out" | grep 'writesample' | awk '{ print $2 }')
22449         readbyte=$(echo "$out" | grep 'readbyte' | awk '{ print $2 }')
22450         writebyte=$(echo "$out" | grep 'writebyte' | awk '{ print $2 }')
22451
22452         [ $readsample -eq 0 ] || error "read sample ($readsample) is wrong"
22453         [ $writesample -eq 0 ] || error "write sample ($writesample) is wrong"
22454         [ $readbyte -eq 0 ] || error "read bytes ($readbyte) is wrong"
22455         [ $writebyte -eq 0 ] || error "write bytes ($writebyte) is wrong"
22456
22457         $LCTL set_param -n llite.*.file_heat=$file_heat_sav
22458         rm -f $DIR/$tfile
22459 }
22460 run_test 813 "File heat verfication"
22461
22462 test_814()
22463 {
22464         dd of=$DIR/$tfile seek=128 bs=1k < /dev/null
22465         echo -n y >> $DIR/$tfile
22466         cp --sparse=always $DIR/$tfile $DIR/${tfile}.cp || error "copy failed"
22467         diff $DIR/$tfile $DIR/${tfile}.cp || error "files should be same"
22468 }
22469 run_test 814 "sparse cp works as expected (LU-12361)"
22470
22471 test_815()
22472 {
22473         writeme -b 100 $DIR/$tfile || error "write 100 bytes failed"
22474         writeme -b 0 $DIR/$tfile || error "write 0 byte failed"
22475 }
22476 run_test 815 "zero byte tiny write doesn't hang (LU-12382)"
22477
22478 test_816() {
22479         [ "$SHARED_KEY" = true ] &&
22480                 skip "OSC connections never go IDLE with Shared-Keys enabled"
22481
22482         $LFS setstripe -c 1 -i 0 $DIR/$tfile
22483         # ensure ost1 is connected
22484         stat $DIR/$tfile >/dev/null || error "can't stat"
22485         wait_osc_import_state client ost1 FULL
22486         # no locks, no reqs to let the connection idle
22487         cancel_lru_locks osc
22488         lru_resize_disable osc
22489         local before
22490         local now
22491         before=$($LCTL get_param -n \
22492                  ldlm.namespaces.$FSNAME-OST0000-osc-[^M]*.lru_size)
22493
22494         wait_osc_import_state client ost1 IDLE
22495         dd if=/dev/null of=$DIR/$tfile bs=1k count=1 conv=sync
22496         now=$($LCTL get_param -n \
22497               ldlm.namespaces.$FSNAME-OST0000-osc-[^M]*.lru_size)
22498         [ $before == $now ] || error "lru_size changed $before != $now"
22499 }
22500 run_test 816 "do not reset lru_resize on idle reconnect"
22501
22502 cleanup_817() {
22503         umount $tmpdir
22504         exportfs -u localhost:$DIR/nfsexp
22505         rm -rf $DIR/nfsexp
22506 }
22507
22508 test_817() {
22509         systemctl restart nfs-server.service || skip "failed to restart nfsd"
22510
22511         mkdir -p $DIR/nfsexp
22512         exportfs -orw,no_root_squash localhost:$DIR/nfsexp ||
22513                 error "failed to export nfs"
22514
22515         tmpdir=$(mktemp -d /tmp/nfs-XXXXXX)
22516         stack_trap cleanup_817 EXIT
22517
22518         mount -t nfs -orw localhost:$DIR/nfsexp $tmpdir ||
22519                 error "failed to mount nfs to $tmpdir"
22520
22521         cp /bin/true $tmpdir
22522         $DIR/nfsexp/true || error "failed to execute 'true' command"
22523 }
22524 run_test 817 "nfsd won't cache write lock for exec file"
22525
22526 test_818() {
22527         mkdir $DIR/$tdir
22528         $LFS setstripe -c1 -i0 $DIR/$tfile
22529         $LFS setstripe -c1 -i1 $DIR/$tfile
22530         stop $SINGLEMDS
22531         #define OBD_FAIL_OSP_CANT_PROCESS_LLOG          0x2105
22532         do_facet $SINGLEMDS lctl set_param fail_loc=0x80002105
22533         start $SINGLEMDS $(mdsdevname ${SINGLEMDS//mds/}) $MDS_MOUNT_OPTS ||
22534                 error "start $SINGLEMDS failed"
22535         rm -rf $DIR/$tdir
22536 }
22537 run_test 818 "unlink with failed llog"
22538
22539 test_819a() {
22540         dd if=/dev/zero of=$DIR/$tfile bs=1M count=1
22541         cancel_lru_locks osc
22542         #define OBD_FAIL_OST_2BIG_NIOBUF                0x248
22543         do_facet $SINGLEMDS lctl set_param fail_loc=0x80000248
22544         dd if=$DIR/$tfile of=/dev/null bs=1M count=1
22545         rm -f $TDIR/$tfile
22546 }
22547 run_test 819a "too big niobuf in read"
22548
22549 test_819b() {
22550         #define OBD_FAIL_OST_2BIG_NIOBUF                0x248
22551         do_facet $SINGLEMDS lctl set_param fail_loc=0x80000248
22552         dd if=/dev/zero of=$DIR/$tfile bs=1M count=1
22553         cancel_lru_locks osc
22554         sleep 1
22555         rm -f $TDIR/$tfile
22556 }
22557 run_test 819b "too big niobuf in write"
22558
22559 #
22560 # tests that do cleanup/setup should be run at the end
22561 #
22562
22563 test_900() {
22564         [ $PARALLEL == "yes" ] && skip "skip parallel run"
22565         local ls
22566
22567         #define OBD_FAIL_MGC_PAUSE_PROCESS_LOG   0x903
22568         $LCTL set_param fail_loc=0x903
22569
22570         cancel_lru_locks MGC
22571
22572         FAIL_ON_ERROR=true cleanup
22573         FAIL_ON_ERROR=true setup
22574 }
22575 run_test 900 "umount should not race with any mgc requeue thread"
22576
22577 complete $SECONDS
22578 [ -f $EXT2_DEV ] && rm $EXT2_DEV || true
22579 check_and_cleanup_lustre
22580 if [ "$I_MOUNTED" != "yes" ]; then
22581         lctl set_param debug="$OLDDEBUG" 2> /dev/null || true
22582 fi
22583 exit_status