Whamcloud - gitweb
4728c75eb15f3a20c98253d543fd943240d89aad
[fs/lustre-release.git] / lustre / tests / sanity.sh
1 #!/bin/bash
2 # -*- tab-width: 4; indent-tabs-mode: t; -*-
3 #
4 # Run select tests by setting ONLY, or as arguments to the script.
5 # Skip specific tests by setting EXCEPT.
6 #
7 # e.g. ONLY="22 23" or ONLY="`seq 32 39`" or EXCEPT="31"
8 set -e
9
10 ONLY=${ONLY:-"$*"}
11 # bug number for skipped test: 13297 2108 9789 3637 9789 3561 12622 5188
12 ALWAYS_EXCEPT="                42a  42b  42c  42d  45   51d   68b   $SANITY_EXCEPT"
13 # UPDATE THE COMMENT ABOVE WITH BUG NUMBERS WHEN CHANGING ALWAYS_EXCEPT!
14
15 # with LOD/OSP landing
16 # bug number for skipped tests: LU-2036
17 ALWAYS_EXCEPT="                 76     $ALWAYS_EXCEPT"
18
19
20 SRCDIR=$(cd $(dirname $0); echo $PWD)
21 export PATH=$PATH:/sbin
22
23 TMP=${TMP:-/tmp}
24
25 CHECKSTAT=${CHECKSTAT:-"checkstat -v"}
26 CREATETEST=${CREATETEST:-createtest}
27 LFS=${LFS:-lfs}
28 LFIND=${LFIND:-"$LFS find"}
29 LVERIFY=${LVERIFY:-ll_dirstripe_verify}
30 LCTL=${LCTL:-lctl}
31 MCREATE=${MCREATE:-mcreate}
32 OPENFILE=${OPENFILE:-openfile}
33 OPENUNLINK=${OPENUNLINK:-openunlink}
34 export MULTIOP=${MULTIOP:-multiop}
35 READS=${READS:-"reads"}
36 MUNLINK=${MUNLINK:-munlink}
37 SOCKETSERVER=${SOCKETSERVER:-socketserver}
38 SOCKETCLIENT=${SOCKETCLIENT:-socketclient}
39 MEMHOG=${MEMHOG:-memhog}
40 DIRECTIO=${DIRECTIO:-directio}
41 ACCEPTOR_PORT=${ACCEPTOR_PORT:-988}
42 UMOUNT=${UMOUNT:-"umount -d"}
43 STRIPES_PER_OBJ=-1
44 CHECK_GRANT=${CHECK_GRANT:-"yes"}
45 GRANT_CHECK_LIST=${GRANT_CHECK_LIST:-""}
46 export PARALLEL=${PARALLEL:-"no"}
47
48 export NAME=${NAME:-local}
49
50 SAVE_PWD=$PWD
51
52 CLEANUP=${CLEANUP:-:}
53 SETUP=${SETUP:-:}
54 TRACE=${TRACE:-""}
55 LUSTRE=${LUSTRE:-$(cd $(dirname $0)/..; echo $PWD)}
56 . $LUSTRE/tests/test-framework.sh
57 init_test_env $@
58 . ${CONFIG:=$LUSTRE/tests/cfg/${NAME}.sh}
59 init_logging
60
61 [ "$SLOW" = "no" ] && EXCEPT_SLOW="24o 27m 64b 68 71 77f 78 115 124b"
62
63 [ $(facet_fstype $SINGLEMDS) = "zfs" ] &&
64 # bug number for skipped test:        LU-1593 LU-2610 LU-2833 LU-1957 LU-2805
65         ALWAYS_EXCEPT="$ALWAYS_EXCEPT 34h     40      48a     180     184c"
66
67 FAIL_ON_ERROR=false
68
69 cleanup() {
70         echo -n "cln.."
71         pgrep ll_sa > /dev/null && { echo "There are ll_sa thread not exit!"; exit 20; }
72         cleanupall ${FORCE} $* || { echo "FAILed to clean up"; exit 20; }
73 }
74 setup() {
75         echo -n "mnt.."
76         load_modules
77         setupall || exit 10
78         echo "done"
79 }
80
81 check_kernel_version() {
82         WANT_VER=$1
83         GOT_VER=$(lctl get_param -n version | awk '/kernel:/ {print $2}')
84         case $GOT_VER in
85         patchless|patchless_client) return 0;;
86         *) [ $GOT_VER -ge $WANT_VER ] && return 0 ;;
87         esac
88         log "test needs at least kernel version $WANT_VER, running $GOT_VER"
89         return 1
90 }
91
92 check_swap_layouts_support()
93 {
94         $LCTL get_param -n llite.*.sbi_flags | grep -q layout ||
95                 { skip "Does not support layout lock."; return 0; }
96         return 1
97 }
98
99 if [ "$ONLY" == "cleanup" ]; then
100        sh llmountcleanup.sh
101        exit 0
102 fi
103
104 check_and_setup_lustre
105
106 DIR=${DIR:-$MOUNT}
107 assert_DIR
108
109 MDT0=$($LCTL get_param -n mdc.*.mds_server_uuid | \
110     awk '{gsub(/_UUID/,""); print $1}' | head -1)
111 LOVNAME=$($LCTL get_param -n llite.*.lov.common_name | tail -n 1)
112 OSTCOUNT=$($LCTL get_param -n lov.$LOVNAME.numobd)
113 STRIPECOUNT=$($LCTL get_param -n lov.$LOVNAME.stripecount)
114 STRIPESIZE=$($LCTL get_param -n lov.$LOVNAME.stripesize)
115 ORIGFREE=$($LCTL get_param -n lov.$LOVNAME.kbytesavail)
116 MAXFREE=${MAXFREE:-$((200000 * $OSTCOUNT))}
117
118 [ -f $DIR/d52a/foo ] && chattr -a $DIR/d52a/foo
119 [ -f $DIR/d52b/foo ] && chattr -i $DIR/d52b/foo
120 rm -rf $DIR/[Rdfs][0-9]*
121
122 # $RUNAS_ID may get set incorrectly somewhere else
123 [ $UID -eq 0 -a $RUNAS_ID -eq 0 ] && error "\$RUNAS_ID set to 0, but \$UID is also 0!"
124
125 check_runas_id $RUNAS_ID $RUNAS_GID $RUNAS
126
127 build_test_filter
128
129 if [ "${ONLY}" = "MOUNT" ] ; then
130         echo "Lustre is up, please go on"
131         exit
132 fi
133
134 echo "preparing for tests involving mounts"
135 EXT2_DEV=${EXT2_DEV:-$TMP/SANITY.LOOP}
136 touch $EXT2_DEV
137 mke2fs -j -F $EXT2_DEV 8000 > /dev/null
138 echo # add a newline after mke2fs.
139
140 umask 077
141
142 OLDDEBUG="`lctl get_param -n debug 2> /dev/null`"
143 lctl set_param debug=-1 2> /dev/null || true
144 test_0() {
145         touch $DIR/$tfile
146         $CHECKSTAT -t file $DIR/$tfile || error
147         rm $DIR/$tfile
148         $CHECKSTAT -a $DIR/$tfile || error
149 }
150 run_test 0 "touch .../$tfile ; rm .../$tfile ====================="
151
152 test_0b() {
153         chmod 0755 $DIR || error
154         $CHECKSTAT -p 0755 $DIR || error
155 }
156 run_test 0b "chmod 0755 $DIR ============================="
157
158 test_0c() {
159     $LCTL get_param mdc.*.import | grep  "state: FULL" || error "import not FULL"
160     $LCTL get_param mdc.*.import | grep  "target: $FSNAME-MDT" || error "bad target"
161 }
162 run_test 0c "check import proc ============================="
163
164 test_1a() {
165         test_mkdir -p $DIR/$tdir
166         test_mkdir -p $DIR/$tdir/d2
167         test_mkdir $DIR/$tdir/d2 && error "we expect EEXIST, but not returned"
168         $CHECKSTAT -t dir $DIR/$tdir/d2 || error
169 }
170 run_test 1a "mkdir .../d1; mkdir .../d1/d2 ====================="
171
172 test_1b() {
173         rmdir $DIR/$tdir/d2
174         rmdir $DIR/$tdir
175         $CHECKSTAT -a $DIR/$tdir || error
176 }
177 run_test 1b "rmdir .../d1/d2; rmdir .../d1 ====================="
178
179 test_2a() {
180         test_mkdir $DIR/$tdir
181         touch $DIR/$tdir/$tfile
182         $CHECKSTAT -t file $DIR/$tdir/$tfile || error
183 }
184 run_test 2a "mkdir .../d2; touch .../d2/f ======================"
185
186 test_2b() {
187         rm -r $DIR/$tdir
188         $CHECKSTAT -a $DIR/$tdir || error
189 }
190 run_test 2b "rm -r .../d2; checkstat .../d2/f ======================"
191
192 test_3a() {
193         test_mkdir -p $DIR/$tdir
194         $CHECKSTAT -t dir $DIR/$tdir || error
195 }
196 run_test 3a "mkdir .../d3 ======================================"
197
198 test_3b() {
199         if [ ! -d $DIR/$tdir ]; then
200                 mkdir $DIR/$tdir
201         fi
202         touch $DIR/$tdir/$tfile
203         $CHECKSTAT -t file $DIR/$tdir/$tfile || error
204 }
205 run_test 3b "touch .../d3/f ===================================="
206
207 test_3c() {
208         rm -r $DIR/$tdir
209         $CHECKSTAT -a $DIR/$tdir || error
210 }
211 run_test 3c "rm -r .../d3 ======================================"
212
213 test_4a() {
214         test_mkdir -p $DIR/$tdir
215         $CHECKSTAT -t dir $DIR/$tdir || error
216 }
217 run_test 4a "mkdir .../d4 ======================================"
218
219 test_4b() {
220         if [ ! -d $DIR/$tdir ]; then
221                 test_mkdir $DIR/$tdir
222         fi
223         test_mkdir $DIR/$tdir/d2
224         mkdir $DIR/$tdir/d2
225         $CHECKSTAT -t dir $DIR/$tdir/d2 || error
226 }
227 run_test 4b "mkdir .../d4/d2 ==================================="
228
229 test_5() {
230         test_mkdir $DIR/$tdir
231         test_mkdir $DIR/$tdir/d2
232         chmod 0707 $DIR/$tdir/d2
233         $CHECKSTAT -t dir -p 0707 $DIR/$tdir/d2 || error
234 }
235 run_test 5 "mkdir .../d5 .../d5/d2; chmod .../d5/d2 ============"
236
237 test_6a() {
238         touch $DIR/$tfile
239         chmod 0666 $DIR/$tfile || error
240         $CHECKSTAT -t file -p 0666 -u \#$UID $DIR/$tfile || error
241 }
242 run_test 6a "touch .../f6a; chmod .../f6a ======================"
243
244 test_6b() {
245         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID" && return
246         if [ ! -f $DIR/$tfile ]; then
247                 touch $DIR/$tfile
248                 chmod 0666 $DIR/$tfile
249         fi
250         $RUNAS chmod 0444 $DIR/$tfile && error
251         $CHECKSTAT -t file -p 0666 -u \#$UID $DIR/$tfile || error
252 }
253 run_test 6b "$RUNAS chmod .../f6a (should return error) =="
254
255 test_6c() {
256         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID" && return
257         touch $DIR/$tfile
258         chown $RUNAS_ID $DIR/$tfile || error
259         $CHECKSTAT -t file -u \#$RUNAS_ID $DIR/$tfile || error
260 }
261 run_test 6c "touch .../f6c; chown .../f6c ======================"
262
263 test_6d() {
264         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID" && return
265         if [ ! -f $DIR/$tfile ]; then
266                 touch $DIR/$tfile
267                 chown $RUNAS_ID $DIR/$tfile
268         fi
269         $RUNAS chown $UID $DIR/$tfile && error
270         $CHECKSTAT -t file -u \#$RUNAS_ID $DIR/$tfile || error
271 }
272 run_test 6d "$RUNAS chown .../f6c (should return error) =="
273
274 test_6e() {
275         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID" && return
276         touch $DIR/$tfile
277         chgrp $RUNAS_ID $DIR/$tfile || error
278         $CHECKSTAT -t file -u \#$UID -g \#$RUNAS_ID $DIR/$tfile || error
279 }
280 run_test 6e "touch .../f6e; chgrp .../f6e ======================"
281
282 test_6f() {
283         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID" && return
284         if [ ! -f $DIR/$tfile ]; then
285                 touch $DIR/$tfile
286                 chgrp $RUNAS_ID $DIR/$tfile
287         fi
288         $RUNAS chgrp $UID $DIR/$tfile && error
289         $CHECKSTAT -t file -u \#$UID -g \#$RUNAS_ID $DIR/$tfile || error
290 }
291 run_test 6f "$RUNAS chgrp .../f6e (should return error) =="
292
293 test_6g() {
294         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID" && return
295         test_mkdir $DIR/$tdir || error
296         chmod 777 $DIR/$tdir || error
297         $RUNAS mkdir $DIR/$tdir/d || error
298         chmod g+s $DIR/$tdir/d || error
299         test_mkdir $DIR/$tdir/d/subdir
300         $CHECKSTAT -g \#$RUNAS_GID $DIR/$tdir/d/subdir || error
301 }
302 run_test 6g "Is new dir in sgid dir inheriting group?"
303
304 test_6h() { # bug 7331
305         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID" && return
306         touch $DIR/$tfile || error "touch failed"
307         chown $RUNAS_ID:$RUNAS_GID $DIR/$tfile || error "initial chown failed"
308         $RUNAS -G$RUNAS_GID chown $RUNAS_ID:0 $DIR/$tfile &&
309                 error "chown worked"
310         $CHECKSTAT -t file -u \#$RUNAS_ID -g \#$RUNAS_GID $DIR/$tfile || error
311 }
312 run_test 6h "$RUNAS chown RUNAS_ID.0 .../f6h (should return error)"
313
314 test_7a() {
315         test_mkdir $DIR/$tdir
316         $MCREATE $DIR/$tdir/$tfile
317         chmod 0666 $DIR/$tdir/$tfile
318         $CHECKSTAT -t file -p 0666 $DIR/$tdir/$tfile || error
319 }
320 run_test 7a "mkdir .../d7; mcreate .../d7/f; chmod .../d7/f ===="
321
322 test_7b() {
323         if [ ! -d $DIR/$tdir ]; then
324                 mkdir $DIR/$tdir
325         fi
326         $MCREATE $DIR/$tdir/$tfile
327         echo -n foo > $DIR/$tdir/$tfile
328         [ "`cat $DIR/$tdir/$tfile`" = "foo" ] || error
329         $CHECKSTAT -t file -s 3 $DIR/$tdir/$tfile || error
330 }
331 run_test 7b "mkdir .../d7; mcreate d7/f2; echo foo > d7/f2 ====="
332
333 test_8() {
334         test_mkdir $DIR/$tdir
335         touch $DIR/$tdir/$tfile
336         chmod 0666 $DIR/$tdir/$tfile
337         $CHECKSTAT -t file -p 0666 $DIR/$tdir/$tfile || error
338 }
339 run_test 8 "mkdir .../d8; touch .../d8/f; chmod .../d8/f ======="
340
341 test_9() {
342         test_mkdir $DIR/$tdir
343         test_mkdir $DIR/$tdir/d2
344         test_mkdir $DIR/$tdir/d2/d3
345         $CHECKSTAT -t dir $DIR/$tdir/d2/d3 || error
346 }
347 run_test 9 "mkdir .../d9 .../d9/d2 .../d9/d2/d3 ================"
348
349 test_10() {
350         test_mkdir $DIR/$tdir
351         test_mkdir $DIR/$tdir/d2
352         touch $DIR/$tdir/d2/$tfile
353         $CHECKSTAT -t file $DIR/$tdir/d2/$tfile || error
354 }
355 run_test 10 "mkdir .../d10 .../d10/d2; touch .../d10/d2/f ======"
356
357 test_11() {
358         test_mkdir $DIR/$tdir
359         test_mkdir $DIR/$tdir/d2
360         chmod 0666 $DIR/$tdir/d2
361         chmod 0705 $DIR/$tdir/d2
362         $CHECKSTAT -t dir -p 0705 $DIR/$tdir/d2 || error
363 }
364 run_test 11 "mkdir .../d11 d11/d2; chmod .../d11/d2 ============"
365
366 test_12() {
367         test_mkdir $DIR/$tdir
368         touch $DIR/$tdir/$tfile
369         chmod 0666 $DIR/$tdir/$tfile
370         chmod 0654 $DIR/$tdir/$tfile
371         $CHECKSTAT -t file -p 0654 $DIR/$tdir/$tfile || error
372 }
373 run_test 12 "touch .../d12/f; chmod .../d12/f .../d12/f ========"
374
375 test_13() {
376         test_mkdir $DIR/$tdir
377         dd if=/dev/zero of=$DIR/$tdir/$tfile count=10
378         >  $DIR/$tdir/$tfile
379         $CHECKSTAT -t file -s 0 $DIR/$tdir/$tfile || error
380 }
381 run_test 13 "creat .../d13/f; dd .../d13/f; > .../d13/f ========"
382
383 test_14() {
384         test_mkdir $DIR/$tdir
385         touch $DIR/$tdir/$tfile
386         rm $DIR/$tdir/$tfile
387         $CHECKSTAT -a $DIR/$tdir/$tfile || error
388 }
389 run_test 14 "touch .../d14/f; rm .../d14/f; rm .../d14/f ======="
390
391 test_15() {
392         test_mkdir $DIR/$tdir
393         touch $DIR/$tdir/$tfile
394         mv $DIR/$tdir/$tfile $DIR/$tdir/${tfile}_2
395         $CHECKSTAT -t file $DIR/$tdir/${tfile}_2 || error
396 }
397 run_test 15 "touch .../d15/f; mv .../d15/f .../d15/f2 =========="
398
399 test_16() {
400         test_mkdir $DIR/$tdir
401         touch $DIR/$tdir/$tfile
402         rm -rf $DIR/$tdir/$tfile
403         $CHECKSTAT -a $DIR/$tdir/$tfile || error
404 }
405 run_test 16 "touch .../d16/f; rm -rf .../d16/f ================="
406
407 test_17a() {
408         test_mkdir -p $DIR/$tdir
409         touch $DIR/$tdir/$tfile
410         ln -s $DIR/$tdir/$tfile $DIR/$tdir/l-exist
411         ls -l $DIR/$tdir
412         $CHECKSTAT -l $DIR/$tdir/$tfile $DIR/$tdir/l-exist || error
413         $CHECKSTAT -f -t f $DIR/$tdir/l-exist || error
414         rm -f $DIR/$tdir/l-exist
415         $CHECKSTAT -a $DIR/$tdir/l-exist || error
416 }
417 run_test 17a "symlinks: create, remove (real) =================="
418
419 test_17b() {
420         test_mkdir -p $DIR/$tdir
421         ln -s no-such-file $DIR/$tdir/l-dangle
422         ls -l $DIR/$tdir
423         $CHECKSTAT -l no-such-file $DIR/$tdir/l-dangle || error
424         $CHECKSTAT -fa $DIR/$tdir/l-dangle || error
425         rm -f $DIR/$tdir/l-dangle
426         $CHECKSTAT -a $DIR/$tdir/l-dangle || error
427 }
428 run_test 17b "symlinks: create, remove (dangling) =============="
429
430 test_17c() { # bug 3440 - don't save failed open RPC for replay
431         test_mkdir -p $DIR/$tdir
432         ln -s foo $DIR/$tdir/$tfile
433         cat $DIR/$tdir/$tfile && error "opened non-existent symlink" || true
434 }
435 run_test 17c "symlinks: open dangling (should return error) ===="
436
437 test_17d() {
438         test_mkdir -p $DIR/$tdir
439         ln -s foo $DIR/$tdir/$tfile
440         touch $DIR/$tdir/$tfile || error "creating to new symlink"
441 }
442 run_test 17d "symlinks: create dangling ========================"
443
444 test_17e() {
445         test_mkdir -p $DIR/$tdir
446         local foo=$DIR/$tdir/$tfile
447         ln -s $foo $foo || error "create symlink failed"
448         ls -l $foo || error "ls -l failed"
449         ls $foo && error "ls not failed" || true
450 }
451 run_test 17e "symlinks: create recursive symlink (should return error) ===="
452
453 test_17f() {
454         test_mkdir -p $DIR/d17f
455         ln -s 1234567890/2234567890/3234567890/4234567890 $DIR/d17f/111
456         ln -s 1234567890/2234567890/3234567890/4234567890/5234567890/6234567890 $DIR/d17f/222
457         ln -s 1234567890/2234567890/3234567890/4234567890/5234567890/6234567890/7234567890/8234567890 $DIR/d17f/333
458         ln -s 1234567890/2234567890/3234567890/4234567890/5234567890/6234567890/7234567890/8234567890/9234567890/a234567890/b234567890 $DIR/d17f/444
459         ln -s 1234567890/2234567890/3234567890/4234567890/5234567890/6234567890/7234567890/8234567890/9234567890/a234567890/b234567890/c234567890/d234567890/f234567890 $DIR/d17f/555
460         ln -s 1234567890/2234567890/3234567890/4234567890/5234567890/6234567890/7234567890/8234567890/9234567890/a234567890/b234567890/c234567890/d234567890/f234567890/aaaaaaaaaa/bbbbbbbbbb/cccccccccc/dddddddddd/eeeeeeeeee/ffffffffff/ $DIR/d17f/666
461         ls -l  $DIR/d17f
462 }
463 run_test 17f "symlinks: long and very long symlink name ========================"
464
465 # str_repeat(S, N) generate a string that is string S repeated N times
466 str_repeat() {
467         local s=$1
468         local n=$2
469         local ret=''
470         while [ $((n -= 1)) -ge 0 ]; do
471                 ret=$ret$s
472         done
473         echo $ret
474 }
475
476 # Long symlinks and LU-2241
477 test_17g() {
478         test_mkdir -p $DIR/$tdir
479         local TESTS="59 60 61 4094 4095"
480
481         # Fix for inode size boundary in 2.1.4
482         [ $(lustre_version_code $SINGLEMDS) -lt $(version_code 2.1.4) ] &&
483                 TESTS="4094 4095"
484
485         # Patch not applied to 2.2 or 2.3 branches
486         [ $(lustre_version_code $SINGLEMDS) -ge $(version_code 2.2.0) ] &&
487         [ $(lustre_version_code $SINGLEMDS) -le $(version_code 2.3.55) ] &&
488                 TESTS="4094 4095"
489
490         for i in $TESTS; do
491                 local SYMNAME=$(str_repeat 'x' $i)
492                 ln -s $SYMNAME $DIR/$tdir/f$i || error "failed $i-char symlink"
493                 readlink $DIR/$tdir/f$i || error "failed $i-char readlink"
494         done
495 }
496 run_test 17g "symlinks: really long symlink name and inode boundaries"
497
498 test_17h() { #bug 17378
499         remote_mds_nodsh && skip "remote MDS with nodsh" && return
500         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
501         local mdt_idx
502         test_mkdir -p $DIR/$tdir
503         if [ $MDSCOUNT -gt 1 ]; then
504                 mdt_idx=$($LFS getdirstripe -i $DIR/$tdir)
505         else
506                 mdt_idx=0
507         fi
508         $SETSTRIPE -c -1 $DIR/$tdir
509 #define OBD_FAIL_MDS_LOV_PREP_CREATE 0x141
510         do_facet mds$((mdt_idx + 1)) lctl set_param fail_loc=0x80000141
511         touch $DIR/$tdir/$tfile || true
512 }
513 run_test 17h "create objects: lov_free_memmd() doesn't lbug"
514
515 test_17i() { #bug 20018
516         remote_mds_nodsh && skip "remote MDS with nodsh" && return
517         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
518         test_mkdir -p $DIR/$tdir
519         local foo=$DIR/$tdir/$tfile
520         local mdt_idx
521         if [ $MDSCOUNT -gt 1 ]; then
522                 mdt_idx=$($LFS getdirstripe -i $DIR/$tdir)
523         else
524                 mdt_idx=0
525         fi
526         ln -s $foo $foo || error "create symlink failed"
527 #define OBD_FAIL_MDS_READLINK_EPROTO     0x143
528         do_facet mds$((mdt_idx + 1)) lctl set_param fail_loc=0x80000143
529         ls -l $foo && error "error not detected"
530         return 0
531 }
532 run_test 17i "don't panic on short symlink"
533
534 test_17k() { #bug 22301
535         rsync --help | grep -q xattr ||
536                 skip_env "$(rsync --version| head -1) does not support xattrs"
537         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
538         test_mkdir -p $DIR/$tdir
539         test_mkdir -p $DIR/$tdir.new
540         touch $DIR/$tdir/$tfile
541         ln -s $DIR/$tdir/$tfile $DIR/$tdir/$tfile.lnk
542         rsync -av -X $DIR/$tdir/ $DIR/$tdir.new ||
543                 error "rsync failed with xattrs enabled"
544 }
545 run_test 17k "symlinks: rsync with xattrs enabled ========================="
546
547 test_17l() { # LU-279
548         mkdir -p $DIR/$tdir
549         touch $DIR/$tdir/$tfile
550         ln -s $DIR/$tdir/$tfile $DIR/$tdir/$tfile.lnk
551         for path in "$DIR/$tdir" "$DIR/$tdir/$tfile" "$DIR/$tdir/$tfile.lnk"; do
552                 # -h to not follow symlinks. -m '' to list all the xattrs.
553                 # grep to remove first line: '# file: $path'.
554                 for xattr in `getfattr -hm '' $path 2>/dev/null | grep -v '^#'`;
555                 do
556                         lgetxattr_size_check $path $xattr ||
557                                 error "lgetxattr_size_check $path $xattr failed"
558                 done
559         done
560 }
561 run_test 17l "Ensure lgetxattr's returned xattr size is consistent ========"
562
563 # LU-1540
564 test_17m() {
565         local short_sym="0123456789"
566         local WDIR=$DIR/${tdir}m
567         local mds_index
568         local devname
569         local cmd
570         local i
571         local rc=0
572
573         [ $(lustre_version_code $SINGLEMDS) -ge $(version_code 2.2.0) ] &&
574         [ $(lustre_version_code $SINGLEMDS) -le $(version_code 2.2.93) ] &&
575                 skip "MDS 2.2.0-2.2.93 do not NUL-terminate symlinks" && return
576
577         [ "$(facet_fstype $SINGLEMDS)" != "ldiskfs" ] &&
578                 skip "only for ldiskfs MDT" && return 0
579
580         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
581
582         mkdir -p $WDIR
583         long_sym=$short_sym
584         # create a long symlink file
585         for ((i = 0; i < 4; ++i)); do
586                 long_sym=${long_sym}${long_sym}
587         done
588
589         echo "create 512 short and long symlink files under $WDIR"
590         for ((i = 0; i < 256; ++i)); do
591                 ln -sf ${long_sym}"a5a5" $WDIR/long-$i
592                 ln -sf ${short_sym}"a5a5" $WDIR/short-$i
593         done
594
595         echo "erase them"
596         rm -f $WDIR/*
597         sync
598         wait_delete_completed
599
600         echo "recreate the 512 symlink files with a shorter string"
601         for ((i = 0; i < 512; ++i)); do
602                 # rewrite the symlink file with a shorter string
603                 ln -sf ${long_sym} $WDIR/long-$i
604                 ln -sf ${short_sym} $WDIR/short-$i
605         done
606
607         mds_index=$($LFS getstripe -M $WDIR)
608         mds_index=$((mds_index+1))
609         devname=$(mdsdevname $mds_index)
610         cmd="$E2FSCK -fnvd $devname"
611
612         echo "stop and checking mds${mds_index}: $cmd"
613         # e2fsck should not return error
614         stop mds${mds_index} -f
615         do_facet mds${mds_index} $cmd || rc=$?
616
617         start mds${mds_index} $devname $MDS_MOUNT_OPTS
618         df $MOUNT > /dev/null 2>&1
619         [ $rc -ne 0 ] && error "e2fsck should not report error upon "\
620                 "short/long symlink MDT: rc=$rc"
621         return $rc
622 }
623 run_test 17m "run e2fsck against MDT which contains short/long symlink"
624
625 check_fs_consistency_17n() {
626         local mdt_index
627         local devname
628         local cmd
629         local rc=0
630
631         for mdt_index in $(seq 1 $MDSCOUNT); do
632                 devname=$(mdsdevname $mdt_index)
633                 cmd="$E2FSCK -fnvd $devname"
634
635                 echo "stop and checking mds${mdt_index}: $cmd"
636                 # e2fsck should not return error
637                 stop mds${mdt_index}
638                 do_facet mds${mdt_index} $cmd || rc=$?
639
640                 start mds${mdt_index} $devname $MDS_MOUNT_OPTS
641                 df $MOUNT > /dev/null 2>&1
642                 [ $rc -ne 0 ] && break
643         done
644         return $rc
645 }
646
647 test_17n() {
648         local i
649
650         [ $(lustre_version_code $SINGLEMDS) -ge $(version_code 2.2.0) ] &&
651         [ $(lustre_version_code $SINGLEMDS) -le $(version_code 2.2.93) ] &&
652                 skip "MDS 2.2.0-2.2.93 do not NUL-terminate symlinks" && return
653
654         [ "$(facet_fstype $SINGLEMDS)" != "ldiskfs" ] &&
655                 skip "only for ldiskfs MDT" && return 0
656
657         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs" && return
658
659         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
660
661         mkdir -p $DIR/$tdir
662         for ((i=0; i<10; i++)); do
663                 $LFS mkdir -i 1 $DIR/$tdir/remote_dir_${i} ||
664                         error "create remote dir error $i"
665                 createmany -o $DIR/$tdir/remote_dir_${i}/f 10 ||
666                         error "create files under remote dir failed $i"
667         done
668
669         check_fs_consistency_17n || error "e2fsck report error"
670
671         for ((i=0;i<10;i++)); do
672                 rm -rf $DIR/$tdir/remote_dir_${i} ||
673                         error "destroy remote dir error $i"
674         done
675
676         check_fs_consistency_17n || error "e2fsck report error"
677 }
678 run_test 17n "run e2fsck against master/slave MDT which contains remote dir"
679
680 test_18() {
681         touch $DIR/f || error "Failed to touch $DIR/f: $?"
682         ls $DIR || error "Failed to ls $DIR: $?"
683 }
684 run_test 18 "touch .../f ; ls ... =============================="
685
686 test_19a() {
687         touch $DIR/f19
688         ls -l $DIR
689         rm $DIR/f19
690         $CHECKSTAT -a $DIR/f19 || error
691 }
692 run_test 19a "touch .../f19 ; ls -l ... ; rm .../f19 ==========="
693
694 test_19b() {
695         ls -l $DIR/f19 && error || true
696 }
697 run_test 19b "ls -l .../f19 (should return error) =============="
698
699 test_19c() {
700         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID -- skipping" && return
701         $RUNAS touch $DIR/f19 && error || true
702 }
703 run_test 19c "$RUNAS touch .../f19 (should return error) =="
704
705 test_19d() {
706         cat $DIR/f19 && error || true
707 }
708 run_test 19d "cat .../f19 (should return error) =============="
709
710 test_20() {
711         touch $DIR/f
712         rm $DIR/f
713         log "1 done"
714         touch $DIR/f
715         rm $DIR/f
716         log "2 done"
717         touch $DIR/f
718         rm $DIR/f
719         log "3 done"
720         $CHECKSTAT -a $DIR/f || error
721 }
722 run_test 20 "touch .../f ; ls -l ... ==========================="
723
724 test_21() {
725         test_mkdir $DIR/d21
726         [ -f $DIR/d21/dangle ] && rm -f $DIR/d21/dangle
727         ln -s dangle $DIR/d21/link
728         echo foo >> $DIR/d21/link
729         cat $DIR/d21/dangle
730         $CHECKSTAT -t link $DIR/d21/link || error
731         $CHECKSTAT -f -t file $DIR/d21/link || error
732 }
733 run_test 21 "write to dangling link ============================"
734
735 test_22() {
736         WDIR=$DIR/$tdir
737         test_mkdir -p $DIR/$tdir
738         chown $RUNAS_ID:$RUNAS_GID $WDIR
739         (cd $WDIR || error "cd $WDIR failed";
740         $RUNAS tar cf - /etc/hosts /etc/sysconfig/network | \
741         $RUNAS tar xf -)
742         ls -lR $WDIR/etc || error "ls -lR $WDIR/etc failed"
743         $CHECKSTAT -t dir $WDIR/etc || error "checkstat -t dir failed"
744         $CHECKSTAT -u \#$RUNAS_ID -g \#$RUNAS_GID $WDIR/etc || error "checkstat -u failed"
745 }
746 run_test 22 "unpack tar archive as non-root user ==============="
747
748 # was test_23
749 test_23a() {
750         test_mkdir -p $DIR/$tdir
751         local file=$DIR/$tdir/$tfile
752
753         openfile -f O_CREAT:O_EXCL $file || error "$file create failed"
754         openfile -f O_CREAT:O_EXCL $file &&
755                 error "$file recreate succeeded" || true
756 }
757 run_test 23a "O_CREAT|O_EXCL in subdir =========================="
758
759 test_23b() { # bug 18988
760         test_mkdir -p $DIR/$tdir
761         local file=$DIR/$tdir/$tfile
762
763         rm -f $file
764         echo foo > $file || error "write filed"
765         echo bar >> $file || error "append filed"
766         $CHECKSTAT -s 8 $file || error "wrong size"
767         rm $file
768 }
769 run_test 23b "O_APPEND check =========================="
770
771 test_24a() {
772         echo '== rename sanity =============================================='
773         echo '-- same directory rename'
774         test_mkdir $DIR/R1
775         touch $DIR/R1/f
776         mv $DIR/R1/f $DIR/R1/g
777         $CHECKSTAT -t file $DIR/R1/g || error
778 }
779 run_test 24a "touch .../R1/f; rename .../R1/f .../R1/g ========="
780
781 test_24b() {
782         test_mkdir $DIR/R2
783         touch $DIR/R2/{f,g}
784         mv $DIR/R2/f $DIR/R2/g
785         $CHECKSTAT -a $DIR/R2/f || error
786         $CHECKSTAT -t file $DIR/R2/g || error
787 }
788 run_test 24b "touch .../R2/{f,g}; rename .../R2/f .../R2/g ====="
789
790 test_24c() {
791         test_mkdir $DIR/R3
792         test_mkdir $DIR/R3/f
793         mv $DIR/R3/f $DIR/R3/g
794         $CHECKSTAT -a $DIR/R3/f || error
795         $CHECKSTAT -t dir $DIR/R3/g || error
796 }
797 run_test 24c "mkdir .../R3/f; rename .../R3/f .../R3/g ========="
798
799 test_24d() {
800         test_mkdir $DIR/R4
801         test_mkdir $DIR/R4/f
802         test_mkdir $DIR/R4/g
803         mrename $DIR/R4/f $DIR/R4/g
804         $CHECKSTAT -a $DIR/R4/f || error
805         $CHECKSTAT -t dir $DIR/R4/g || error
806 }
807 run_test 24d "mkdir .../R4/{f,g}; rename .../R4/f .../R4/g ====="
808
809 test_24e() {
810         echo '-- cross directory renames --'
811         test_mkdir $DIR/R5a
812         test_mkdir $DIR/R5b
813         touch $DIR/R5a/f
814         mv $DIR/R5a/f $DIR/R5b/g
815         $CHECKSTAT -a $DIR/R5a/f || error
816         $CHECKSTAT -t file $DIR/R5b/g || error
817 }
818 run_test 24e "touch .../R5a/f; rename .../R5a/f .../R5b/g ======"
819
820 test_24f() {
821         test_mkdir $DIR/R6a
822         test_mkdir $DIR/R6b
823         touch $DIR/R6a/f $DIR/R6b/g
824         mv $DIR/R6a/f $DIR/R6b/g
825         $CHECKSTAT -a $DIR/R6a/f || error
826         $CHECKSTAT -t file $DIR/R6b/g || error
827 }
828 run_test 24f "touch .../R6a/f R6b/g; mv .../R6a/f .../R6b/g ===="
829
830 test_24g() {
831         test_mkdir $DIR/R7a
832         test_mkdir $DIR/R7b
833         test_mkdir $DIR/R7a/d
834         mv $DIR/R7a/d $DIR/R7b/e
835         $CHECKSTAT -a $DIR/R7a/d || error
836         $CHECKSTAT -t dir $DIR/R7b/e || error
837 }
838 run_test 24g "mkdir .../R7{a,b}/d; mv .../R7a/d .../R7b/e ======"
839
840 test_24h() {
841         test_mkdir $DIR/R8a
842         test_mkdir $DIR/R8b
843         test_mkdir $DIR/R8a/d
844         test_mkdir $DIR/R8b/e
845         mrename $DIR/R8a/d $DIR/R8b/e
846         $CHECKSTAT -a $DIR/R8a/d || error
847         $CHECKSTAT -t dir $DIR/R8b/e || error
848 }
849 run_test 24h "mkdir .../R8{a,b}/{d,e}; rename .../R8a/d .../R8b/e"
850
851 test_24i() {
852         echo "-- rename error cases"
853         test_mkdir $DIR/R9
854         test_mkdir $DIR/R9/a
855         touch $DIR/R9/f
856         mrename $DIR/R9/f $DIR/R9/a
857         $CHECKSTAT -t file $DIR/R9/f || error
858         $CHECKSTAT -t dir  $DIR/R9/a || error
859         $CHECKSTAT -a $DIR/R9/a/f || error
860 }
861 run_test 24i "rename file to dir error: touch f ; mkdir a ; rename f a"
862
863 test_24j() {
864         test_mkdir $DIR/R10
865         mrename $DIR/R10/f $DIR/R10/g
866         $CHECKSTAT -t dir $DIR/R10 || error
867         $CHECKSTAT -a $DIR/R10/f || error
868         $CHECKSTAT -a $DIR/R10/g || error
869 }
870 run_test 24j "source does not exist ============================"
871
872 test_24k() {
873         test_mkdir $DIR/R11a
874         test_mkdir $DIR/R11a/d
875         touch $DIR/R11a/f
876         mv $DIR/R11a/f $DIR/R11a/d
877         $CHECKSTAT -a $DIR/R11a/f || error
878         $CHECKSTAT -t file $DIR/R11a/d/f || error
879 }
880 run_test 24k "touch .../R11a/f; mv .../R11a/f .../R11a/d ======="
881
882 # bug 2429 - rename foo foo foo creates invalid file
883 test_24l() {
884         f="$DIR/f24l"
885         $MULTIOP $f OcNs || error
886 }
887 run_test 24l "Renaming a file to itself ========================"
888
889 test_24m() {
890         f="$DIR/f24m"
891         $MULTIOP $f OcLN ${f}2 ${f}2 || error "link ${f}2 ${f}2 failed"
892         # on ext3 this does not remove either the source or target files
893         # though the "expected" operation would be to remove the source
894         $CHECKSTAT -t file ${f} || error "${f} missing"
895         $CHECKSTAT -t file ${f}2 || error "${f}2 missing"
896 }
897 run_test 24m "Renaming a file to a hard link to itself ========="
898
899 test_24n() {
900     f="$DIR/f24n"
901     # this stats the old file after it was renamed, so it should fail
902     touch ${f}
903     $CHECKSTAT ${f}
904     mv ${f} ${f}.rename
905     $CHECKSTAT ${f}.rename
906     $CHECKSTAT -a ${f}
907 }
908 run_test 24n "Statting the old file after renaming (Posix rename 2)"
909
910 test_24o() {
911         check_kernel_version 37 || return 0
912         test_mkdir -p $DIR/d24o
913         rename_many -s random -v -n 10 $DIR/d24o
914 }
915 run_test 24o "rename of files during htree split ==============="
916
917 test_24p() {
918         test_mkdir $DIR/R12a
919         test_mkdir $DIR/R12b
920         DIRINO=`ls -lid $DIR/R12a | awk '{ print $1 }'`
921         mrename $DIR/R12a $DIR/R12b
922         $CHECKSTAT -a $DIR/R12a || error
923         $CHECKSTAT -t dir $DIR/R12b || error
924         DIRINO2=`ls -lid $DIR/R12b | awk '{ print $1 }'`
925         [ "$DIRINO" = "$DIRINO2" ] || error "R12a $DIRINO != R12b $DIRINO2"
926 }
927 run_test 24p "mkdir .../R12{a,b}; rename .../R12a .../R12b"
928
929 cleanup_multiop_pause() {
930         trap 0
931         kill -USR1 $MULTIPID
932 }
933
934 test_24q() {
935         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
936         test_mkdir $DIR/R13a
937         test_mkdir $DIR/R13b
938         local DIRINO=$(ls -lid $DIR/R13a | awk '{ print $1 }')
939         multiop_bg_pause $DIR/R13b D_c || error "multiop failed to start"
940         MULTIPID=$!
941
942         trap cleanup_multiop_pause EXIT
943         mrename $DIR/R13a $DIR/R13b
944         $CHECKSTAT -a $DIR/R13a || error "R13a still exists"
945         $CHECKSTAT -t dir $DIR/R13b || error "R13b does not exist"
946         local DIRINO2=$(ls -lid $DIR/R13b | awk '{ print $1 }')
947         [ "$DIRINO" = "$DIRINO2" ] || error "R13a $DIRINO != R13b $DIRINO2"
948         cleanup_multiop_pause
949         wait $MULTIPID || error "multiop close failed"
950 }
951 run_test 24q "mkdir .../R13{a,b}; open R13b rename R13a R13b ==="
952
953 test_24r() { #bug 3789
954         test_mkdir $DIR/R14a
955         test_mkdir $DIR/R14a/b
956         mrename $DIR/R14a $DIR/R14a/b && error "rename to subdir worked!"
957         $CHECKSTAT -t dir $DIR/R14a || error "$DIR/R14a missing"
958         $CHECKSTAT -t dir $DIR/R14a/b || error "$DIR/R14a/b missing"
959 }
960 run_test 24r "mkdir .../R14a/b; rename .../R14a .../R14a/b ====="
961
962 test_24s() {
963         test_mkdir $DIR/R15a
964         test_mkdir $DIR/R15a/b
965         test_mkdir $DIR/R15a/b/c
966         mrename $DIR/R15a $DIR/R15a/b/c && error "rename to sub-subdir worked!"
967         $CHECKSTAT -t dir $DIR/R15a || error "$DIR/R15a missing"
968         $CHECKSTAT -t dir $DIR/R15a/b/c || error "$DIR/R15a/b/c missing"
969 }
970 run_test 24s "mkdir .../R15a/b/c; rename .../R15a .../R15a/b/c ="
971 test_24t() {
972         test_mkdir $DIR/R16a
973         test_mkdir $DIR/R16a/b
974         test_mkdir $DIR/R16a/b/c
975         mrename $DIR/R16a/b/c $DIR/R16a && error "rename to sub-subdir worked!"
976         $CHECKSTAT -t dir $DIR/R16a || error "$DIR/R16a missing"
977         $CHECKSTAT -t dir $DIR/R16a/b/c || error "$DIR/R16a/b/c missing"
978 }
979 run_test 24t "mkdir .../R16a/b/c; rename .../R16a/b/c .../R16a ="
980
981 test_24u() { # bug12192
982         rm -rf $DIR/$tfile
983         $MULTIOP $DIR/$tfile C2w$((2048 * 1024))c || error
984         $CHECKSTAT -s $((2048 * 1024)) $DIR/$tfile || error "wrong file size"
985 }
986 run_test 24u "create stripe file"
987
988 page_size() {
989         getconf PAGE_SIZE
990 }
991
992 simple_cleanup_common() {
993         trap 0
994         rm -rf $DIR/$tdir
995         wait_delete_completed
996 }
997
998 max_pages_per_rpc() {
999         $LCTL get_param -n mdc.*.max_pages_per_rpc | head -1
1000 }
1001
1002 test_24v() {
1003         local NRFILES=100000
1004         local FREE_INODES=$(lfs_df -i | grep "summary" | awk '{print $4}')
1005         [ $FREE_INODES -lt $NRFILES ] && \
1006                 skip "not enough free inodes $FREE_INODES required $NRFILES" &&
1007                 return
1008
1009         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1010         trap simple_cleanup_common EXIT
1011
1012         mkdir -p $DIR/$tdir
1013         createmany -m $DIR/$tdir/$tfile $NRFILES
1014
1015         cancel_lru_locks mdc
1016         lctl set_param mdc.*.stats clear
1017
1018         ls $DIR/$tdir >/dev/null || error "error in listing large dir"
1019
1020         # LU-5 large readdir
1021         # DIRENT_SIZE = 32 bytes for sizeof(struct lu_dirent) +
1022         #               8 bytes for name(filename is mostly 5 in this test) +
1023         #               8 bytes for luda_type
1024         # take into account of overhead in lu_dirpage header and end mark in
1025         # each page, plus one in RPC_NUM calculation.
1026         DIRENT_SIZE=48
1027         RPC_SIZE=$(($(max_pages_per_rpc) * $(page_size)))
1028         RPC_NUM=$(((NRFILES * DIRENT_SIZE + RPC_SIZE - 1) / RPC_SIZE + 1))
1029         mds_readpage=$(lctl get_param mdc.*MDT0000*.stats | \
1030                                 awk '/^mds_readpage/ {print $2}')
1031         [ $mds_readpage -gt $RPC_NUM ] && \
1032                 error "large readdir doesn't take effect"
1033
1034         simple_cleanup_common
1035 }
1036 run_test 24v "list directory with large files (handle hash collision, bug: 17560)"
1037
1038 test_24w() { # bug21506
1039         SZ1=234852
1040         dd if=/dev/zero of=$DIR/$tfile bs=1M count=1 seek=4096 || return 1
1041         dd if=/dev/zero bs=$SZ1 count=1 >> $DIR/$tfile || return 2
1042         dd if=$DIR/$tfile of=$DIR/${tfile}_left bs=1M skip=4097 || return 3
1043         SZ2=`ls -l $DIR/${tfile}_left | awk '{print $5}'`
1044         [ "$SZ1" = "$SZ2" ] || \
1045                 error "Error reading at the end of the file $tfile"
1046 }
1047 run_test 24w "Reading a file larger than 4Gb"
1048
1049 test_24x() {
1050         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs" && return
1051         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1052         local MDTIDX=1
1053         local remote_dir=$DIR/$tdir/remote_dir
1054
1055         mkdir -p $DIR/$tdir
1056         $LFS mkdir -i $MDTIDX $remote_dir ||
1057                 error "create remote directory failed"
1058
1059         mkdir -p $DIR/$tdir/src_dir
1060         touch $DIR/$tdir/src_file
1061         mkdir -p $remote_dir/tgt_dir
1062         touch $remote_dir/tgt_file
1063
1064         mrename $DIR/$tdir/src_dir $remote_dir/tgt_dir &&
1065                 error "rename dir cross MDT works!"
1066
1067         mrename $DIR/$tdir/src_file $remote_dir/tgt_file &&
1068                 error "rename file cross MDT works!"
1069
1070         ln $DIR/$tdir/src_file $remote_dir/tgt_file1 &&
1071                 error "ln file cross MDT should not work!"
1072
1073         rm -rf $DIR/$tdir || error "Can not delete directories"
1074 }
1075 run_test 24x "cross rename/link should be failed"
1076
1077 test_24y() {
1078         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs" && return
1079         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1080         local MDTIDX=1
1081         local remote_dir=$DIR/$tdir/remote_dir
1082
1083         mkdir -p $DIR/$tdir
1084         $LFS mkdir -i $MDTIDX $remote_dir ||
1085                    error "create remote directory failed"
1086
1087         mkdir -p $remote_dir/src_dir
1088         touch $remote_dir/src_file
1089         mkdir -p $remote_dir/tgt_dir
1090         touch $remote_dir/tgt_file
1091
1092         mrename $remote_dir/src_dir $remote_dir/tgt_dir ||
1093                 error "rename subdir in the same remote dir failed!"
1094
1095         mrename $remote_dir/src_file $remote_dir/tgt_file ||
1096                 error "rename files in the same remote dir failed!"
1097
1098         ln $remote_dir/tgt_file $remote_dir/tgt_file1 ||
1099                 error "link files in the same remote dir failed!"
1100
1101         rm -rf $DIR/$tdir || error "Can not delete directories"
1102 }
1103 run_test 24y "rename/link on the same dir should succeed"
1104
1105 test_24z() {
1106         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs" && return
1107         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1108         local MDTIDX=1
1109         local remote_src=$DIR/$tdir/remote_dir
1110         local remote_tgt=$DIR/$tdir/remote_tgt
1111
1112         mkdir -p $DIR/$tdir
1113         $LFS mkdir -i $MDTIDX $remote_src ||
1114                    error "create remote directory failed"
1115
1116         $LFS mkdir -i $MDTIDX $remote_tgt ||
1117                    error "create remote directory failed"
1118
1119         mrename $remote_src $remote_tgt &&
1120                 error "rename remote dirs should not work!"
1121
1122         # If target dir does not exists, it should succeed
1123         rm -rf $remote_tgt
1124         mrename $remote_src $remote_tgt ||
1125                 error "rename remote dirs(tgt dir does not exists) failed!"
1126
1127         rm -rf $DIR/$tdir || error "Can not delete directories"
1128 }
1129 run_test 24z "rename one remote dir to another remote dir should fail"
1130
1131 test_25a() {
1132         echo '== symlink sanity ============================================='
1133
1134         test_mkdir $DIR/d25
1135         ln -s d25 $DIR/s25
1136         touch $DIR/s25/foo || error
1137 }
1138 run_test 25a "create file in symlinked directory ==============="
1139
1140 test_25b() {
1141         [ ! -d $DIR/d25 ] && test_25a
1142         $CHECKSTAT -t file $DIR/s25/foo || error
1143 }
1144 run_test 25b "lookup file in symlinked directory ==============="
1145
1146 test_26a() {
1147         test_mkdir $DIR/d26
1148         test_mkdir $DIR/d26/d26-2
1149         ln -s d26/d26-2 $DIR/s26
1150         touch $DIR/s26/foo || error
1151 }
1152 run_test 26a "multiple component symlink ======================="
1153
1154 test_26b() {
1155         test_mkdir -p $DIR/d26b/d26-2
1156         ln -s d26b/d26-2/foo $DIR/s26-2
1157         touch $DIR/s26-2 || error
1158 }
1159 run_test 26b "multiple component symlink at end of lookup ======"
1160
1161 test_26c() {
1162         test_mkdir $DIR/d26.2
1163         touch $DIR/d26.2/foo
1164         ln -s d26.2 $DIR/s26.2-1
1165         ln -s s26.2-1 $DIR/s26.2-2
1166         ln -s s26.2-2 $DIR/s26.2-3
1167         chmod 0666 $DIR/s26.2-3/foo
1168 }
1169 run_test 26c "chain of symlinks ================================"
1170
1171 # recursive symlinks (bug 439)
1172 test_26d() {
1173         ln -s d26-3/foo $DIR/d26-3
1174 }
1175 run_test 26d "create multiple component recursive symlink ======"
1176
1177 test_26e() {
1178         [ ! -h $DIR/d26-3 ] && test_26d
1179         rm $DIR/d26-3
1180 }
1181 run_test 26e "unlink multiple component recursive symlink ======"
1182
1183 # recursive symlinks (bug 7022)
1184 test_26f() {
1185         test_mkdir -p $DIR/$tdir
1186         test_mkdir $DIR/$tdir/$tfile   || error "mkdir $DIR/$tdir/$tfile failed"
1187         cd $DIR/$tdir/$tfile           || error "cd $DIR/$tdir/$tfile failed"
1188         test_mkdir -p lndir bar1      || error "mkdir lndir/bar1 failed"
1189         test_mkdir $DIR/$tdir/$tfile/$tfile   || error "mkdir $tfile failed"
1190         cd $tfile                || error "cd $tfile failed"
1191         ln -s .. dotdot          || error "ln dotdot failed"
1192         ln -s dotdot/lndir lndir || error "ln lndir failed"
1193         cd $DIR/$tdir                 || error "cd $DIR/$tdir failed"
1194         output=`ls $tfile/$tfile/lndir/bar1`
1195         [ "$output" = bar1 ] && error "unexpected output"
1196         rm -r $tfile             || error "rm $tfile failed"
1197         $CHECKSTAT -a $DIR/$tfile || error "$tfile not gone"
1198 }
1199 run_test 26f "rm -r of a directory which has recursive symlink ="
1200
1201 test_27a() {
1202         echo '== stripe sanity =============================================='
1203         test_mkdir -p $DIR/d27 || error "mkdir failed"
1204         $GETSTRIPE $DIR/d27
1205         $SETSTRIPE -c 1 $DIR/d27/f0 || error "setstripe failed"
1206         $CHECKSTAT -t file $DIR/d27/f0 || error "checkstat failed"
1207         pass
1208         log "== test_27a: write to one stripe file ========================="
1209         cp /etc/hosts $DIR/d27/f0 || error
1210 }
1211 run_test 27a "one stripe file =================================="
1212
1213 test_27b() {
1214         [ "$OSTCOUNT" -lt "2" ] && skip_env "skipping 2-stripe test" && return
1215         test_mkdir -p $DIR/d27
1216         $SETSTRIPE -c 2 $DIR/d27/f01 || error "setstripe failed"
1217         $GETSTRIPE -c $DIR/d27/f01
1218         [ $($GETSTRIPE -c $DIR/d27/f01) -eq 2 ] ||
1219                 error "two-stripe file doesn't have two stripes"
1220 }
1221 run_test 27b "create two stripe file"
1222
1223 test_27c() {
1224         [ -f $DIR/d27/f01 ] || skip "test_27b not run" && return
1225
1226         dd if=/dev/zero of=$DIR/d27/f01 bs=4k count=4 || error "dd failed"
1227 }
1228 run_test 27c "write to two stripe file"
1229
1230 test_27d() {
1231         test_mkdir -p $DIR/d27
1232         $SETSTRIPE -c 0 -i -1 -S 0 $DIR/d27/fdef || error "setstripe failed"
1233         $CHECKSTAT -t file $DIR/d27/fdef || error "checkstat failed"
1234         dd if=/dev/zero of=$DIR/d27/fdef bs=4k count=4 || error
1235 }
1236 run_test 27d "create file with default settings ================"
1237
1238 test_27e() {
1239         test_mkdir -p $DIR/d27
1240         $SETSTRIPE -c 2 $DIR/d27/f12 || error "setstripe failed"
1241         $SETSTRIPE -c 2 $DIR/d27/f12 && error "setstripe succeeded twice"
1242         $CHECKSTAT -t file $DIR/d27/f12 || error "checkstat failed"
1243 }
1244 run_test 27e "setstripe existing file (should return error) ======"
1245
1246 test_27f() {
1247         test_mkdir -p $DIR/d27
1248         $SETSTRIPE -S 100 -i 0 -c 1 $DIR/d27/fbad && error "setstripe failed"
1249         dd if=/dev/zero of=$DIR/d27/fbad bs=4k count=4 || error "dd failed"
1250         $GETSTRIPE $DIR/d27/fbad || error "$GETSTRIPE failed"
1251 }
1252 run_test 27f "setstripe with bad stripe size (should return error)"
1253
1254 test_27g() {
1255         test_mkdir -p $DIR/d27
1256         $MCREATE $DIR/d27/fnone || error "mcreate failed"
1257         $GETSTRIPE $DIR/d27/fnone 2>&1 | grep "no stripe info" ||
1258                 error "$DIR/d27/fnone has object"
1259 }
1260 run_test 27g "$GETSTRIPE with no objects"
1261
1262 test_27i() {
1263         touch $DIR/d27/fsome || error "touch failed"
1264         [ $($GETSTRIPE -c $DIR/d27/fsome) -gt 0 ] || error "missing objects"
1265 }
1266 run_test 27i "$GETSTRIPE with some objects"
1267
1268 test_27j() {
1269         test_mkdir -p $DIR/d27
1270         $SETSTRIPE -i $OSTCOUNT $DIR/d27/f27j && error "setstripe failed"||true
1271 }
1272 run_test 27j "setstripe with bad stripe offset (should return error)"
1273
1274 test_27k() { # bug 2844
1275         test_mkdir -p $DIR/d27
1276         FILE=$DIR/d27/f27k
1277         LL_MAX_BLKSIZE=$((4 * 1024 * 1024))
1278         [ ! -d $DIR/d27 ] && test_mkdir -p $DIR d27
1279         $SETSTRIPE -S 67108864 $FILE || error "setstripe failed"
1280         BLKSIZE=`stat $FILE | awk '/IO Block:/ { print $7 }'`
1281         [ $BLKSIZE -le $LL_MAX_BLKSIZE ] || error "$BLKSIZE > $LL_MAX_BLKSIZE"
1282         dd if=/dev/zero of=$FILE bs=4k count=1
1283         BLKSIZE=`stat $FILE | awk '/IO Block:/ { print $7 }'`
1284         [ $BLKSIZE -le $LL_MAX_BLKSIZE ] || error "$BLKSIZE > $LL_MAX_BLKSIZE"
1285 }
1286 run_test 27k "limit i_blksize for broken user apps ============="
1287
1288 test_27l() {
1289         test_mkdir -p $DIR/d27
1290         mcreate $DIR/f27l || error "creating file"
1291         $RUNAS $SETSTRIPE -c 1 $DIR/f27l && \
1292                 error "setstripe should have failed" || true
1293 }
1294 run_test 27l "check setstripe permissions (should return error)"
1295
1296 test_27m() {
1297         [ "$OSTCOUNT" -lt "2" ] && skip_env "$OSTCOUNT < 2 OSTs -- skipping" &&
1298                 return
1299         if [ $ORIGFREE -gt $MAXFREE ]; then
1300                 skip "$ORIGFREE > $MAXFREE skipping out-of-space test on OST0"
1301                 return
1302         fi
1303         trap simple_cleanup_common EXIT
1304         test_mkdir -p $DIR/$tdir
1305         $SETSTRIPE -i 0 -c 1 $DIR/$tdir/f27m_1
1306         dd if=/dev/zero of=$DIR/$tdir/f27m_1 bs=1024 count=$MAXFREE &&
1307                 error "dd should fill OST0"
1308         i=2
1309         while $SETSTRIPE -i 0 -c 1 $DIR/$tdir/f27m_$i; do
1310                 i=`expr $i + 1`
1311                 [ $i -gt 256 ] && break
1312         done
1313         i=`expr $i + 1`
1314         touch $DIR/$tdir/f27m_$i
1315         [ `$GETSTRIPE $DIR/$tdir/f27m_$i | grep -A 10 obdidx | awk '{print $1}'| grep -w "0"` ] &&
1316                 error "OST0 was full but new created file still use it"
1317         i=`expr $i + 1`
1318         touch $DIR/$tdir/f27m_$i
1319         [ `$GETSTRIPE $DIR/$tdir/f27m_$i | grep -A 10 obdidx | awk '{print $1}'| grep -w "0"` ] &&
1320                 error "OST0 was full but new created file still use it"
1321         simple_cleanup_common
1322 }
1323 run_test 27m "create file while OST0 was full =================="
1324
1325 sleep_maxage() {
1326         local DELAY=$(do_facet $SINGLEMDS lctl get_param -n lov.*.qos_maxage | head -n 1 | awk '{print $1 * 2}')
1327         sleep $DELAY
1328 }
1329
1330 # OSCs keep a NOSPC flag that will be reset after ~5s (qos_maxage)
1331 # if the OST isn't full anymore.
1332 reset_enospc() {
1333         local OSTIDX=${1:-""}
1334
1335         local list=$(comma_list $(osts_nodes))
1336         [ "$OSTIDX" ] && list=$(facet_host ost$((OSTIDX + 1)))
1337
1338         do_nodes $list lctl set_param fail_loc=0
1339         sync    # initiate all OST_DESTROYs from MDS to OST
1340         sleep_maxage
1341 }
1342
1343 exhaust_precreations() {
1344         local OSTIDX=$1
1345         local FAILLOC=$2
1346         local FAILIDX=${3:-$OSTIDX}
1347
1348         test_mkdir -p $DIR/$tdir
1349         local MDSIDX=$(get_mds_dir "$DIR/$tdir")
1350         echo OSTIDX=$OSTIDX MDSIDX=$MDSIDX
1351
1352         local OST=$(ostname_from_index $OSTIDX)
1353         local MDT_INDEX=$(lfs df | grep "\[MDT:$((MDSIDX - 1))\]" | awk '{print $1}' | \
1354                           sed -e 's/_UUID$//;s/^.*-//')
1355
1356         # on the mdt's osc
1357         local mdtosc_proc1=$(get_mdtosc_proc_path mds${MDSIDX} $OST)
1358         local last_id=$(do_facet mds${MDSIDX} lctl get_param -n \
1359         osc.$mdtosc_proc1.prealloc_last_id)
1360         local next_id=$(do_facet mds${MDSIDX} lctl get_param -n \
1361         osc.$mdtosc_proc1.prealloc_next_id)
1362
1363         local mdtosc_proc2=$(get_mdtosc_proc_path mds${MDSIDX})
1364         do_facet mds${MDSIDX} lctl get_param osc.$mdtosc_proc2.prealloc*
1365
1366         test_mkdir -p $DIR/$tdir/${OST}
1367         $SETSTRIPE -i $OSTIDX -c 1 $DIR/$tdir/${OST}
1368 #define OBD_FAIL_OST_ENOSPC              0x215
1369         do_facet ost$((OSTIDX + 1)) lctl set_param fail_val=$FAILIDX
1370         do_facet ost$((OSTIDX + 1)) lctl set_param fail_loc=0x215
1371         echo "Creating to objid $last_id on ost $OST..."
1372         createmany -o $DIR/$tdir/${OST}/f $next_id $((last_id - next_id + 2))
1373         do_facet mds${MDSIDX} lctl get_param osc.$mdtosc_proc2.prealloc*
1374         do_facet ost$((OSTIDX + 1)) lctl set_param fail_loc=$FAILLOC
1375         sleep_maxage
1376 }
1377
1378 exhaust_all_precreations() {
1379         local i
1380         for (( i=0; i < OSTCOUNT; i++ )) ; do
1381                 exhaust_precreations $i $1 -1
1382         done
1383 }
1384
1385 test_27n() {
1386         [ "$OSTCOUNT" -lt "2" ] && skip_env "too few OSTs" && return
1387         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1388         remote_mds_nodsh && skip "remote MDS with nodsh" && return
1389         remote_ost_nodsh && skip "remote OST with nodsh" && return
1390
1391         reset_enospc
1392         rm -f $DIR/$tdir/$tfile
1393         exhaust_precreations 0 0x80000215
1394         $SETSTRIPE -c -1 $DIR/$tdir
1395         touch $DIR/$tdir/$tfile || error
1396         $GETSTRIPE $DIR/$tdir/$tfile
1397         reset_enospc
1398 }
1399 run_test 27n "create file with some full OSTs =================="
1400
1401 test_27o() {
1402         [ "$OSTCOUNT" -lt "2" ] && skip_env "too few OSTs" && return
1403         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1404         remote_mds_nodsh && skip "remote MDS with nodsh" && return
1405         remote_ost_nodsh && skip "remote OST with nodsh" && return
1406
1407         reset_enospc
1408         rm -f $DIR/$tdir/$tfile
1409         exhaust_all_precreations 0x215
1410
1411         touch $DIR/$tdir/$tfile && error "able to create $DIR/$tdir/$tfile"
1412
1413         reset_enospc
1414         rm -rf $DIR/$tdir/*
1415 }
1416 run_test 27o "create file with all full OSTs (should error) ===="
1417
1418 test_27p() {
1419         [ "$OSTCOUNT" -lt "2" ] && skip_env "too few OSTs" && return
1420         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1421         remote_mds_nodsh && skip "remote MDS with nodsh" && return
1422         remote_ost_nodsh && skip "remote OST with nodsh" && return
1423
1424         reset_enospc
1425         rm -f $DIR/$tdir/$tfile
1426         test_mkdir -p $DIR/$tdir
1427
1428         $MCREATE $DIR/$tdir/$tfile || error "mcreate failed"
1429         $TRUNCATE $DIR/$tdir/$tfile 80000000 || error "truncate failed"
1430         $CHECKSTAT -s 80000000 $DIR/$tdir/$tfile || error "checkstat failed"
1431
1432         exhaust_precreations 0 0x80000215
1433         echo foo >> $DIR/$tdir/$tfile || error "append failed"
1434         $CHECKSTAT -s 80000004 $DIR/$tdir/$tfile || error "checkstat failed"
1435         $GETSTRIPE $DIR/$tdir/$tfile
1436
1437         reset_enospc
1438 }
1439 run_test 27p "append to a truncated file with some full OSTs ==="
1440
1441 test_27q() {
1442         [ "$OSTCOUNT" -lt "2" ] && skip_env "too few OSTs" && return
1443         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1444         remote_mds_nodsh && skip "remote MDS with nodsh" && return
1445         remote_ost_nodsh && skip "remote OST with nodsh" && return
1446
1447         reset_enospc
1448         rm -f $DIR/$tdir/$tfile
1449
1450         test_mkdir -p $DIR/$tdir
1451         $MCREATE $DIR/$tdir/$tfile || error "mcreate $DIR/$tdir/$tfile failed"
1452         $TRUNCATE $DIR/$tdir/$tfile 80000000 ||error "truncate $DIR/$tdir/$tfile failed"
1453         $CHECKSTAT -s 80000000 $DIR/$tdir/$tfile || error "checkstat failed"
1454
1455         exhaust_all_precreations 0x215
1456
1457         echo foo >> $DIR/$tdir/$tfile && error "append succeeded"
1458         $CHECKSTAT -s 80000000 $DIR/$tdir/$tfile || error "checkstat 2 failed"
1459
1460         reset_enospc
1461 }
1462 run_test 27q "append to truncated file with all OSTs full (should error) ==="
1463
1464 test_27r() {
1465         [ "$OSTCOUNT" -lt "2" ] && skip_env "too few OSTs" && return
1466         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1467         remote_mds_nodsh && skip "remote MDS with nodsh" && return
1468         remote_ost_nodsh && skip "remote OST with nodsh" && return
1469
1470         reset_enospc
1471         rm -f $DIR/$tdir/$tfile
1472         exhaust_precreations 0 0x80000215
1473
1474         $SETSTRIPE -i 0 -c 2 $DIR/$tdir/$tfile # && error
1475
1476         reset_enospc
1477 }
1478 run_test 27r "stripe file with some full OSTs (shouldn't LBUG) ="
1479
1480 test_27s() { # bug 10725
1481         test_mkdir -p $DIR/$tdir
1482         local stripe_size=$((4096 * 1024 * 1024))       # 2^32
1483         local stripe_count=0
1484         [ $OSTCOUNT -eq 1 ] || stripe_count=2
1485         $SETSTRIPE -S $stripe_size -c $stripe_count $DIR/$tdir &&
1486                 error "stripe width >= 2^32 succeeded" || true
1487
1488 }
1489 run_test 27s "lsm_xfersize overflow (should error) (bug 10725)"
1490
1491 test_27t() { # bug 10864
1492         WDIR=`pwd`
1493         WLFS=`which lfs`
1494         cd $DIR
1495         touch $tfile
1496         $WLFS getstripe $tfile
1497         cd $WDIR
1498 }
1499 run_test 27t "check that utils parse path correctly"
1500
1501 test_27u() { # bug 4900
1502         [ "$OSTCOUNT" -lt "2" ] && skip_env "too few OSTs" && return
1503         remote_mds_nodsh && skip "remote MDS with nodsh" && return
1504         local index
1505         local list=$(comma_list $(mdts_nodes))
1506
1507 #define OBD_FAIL_MDS_OSC_PRECREATE      0x139
1508         do_nodes $list $LCTL set_param fail_loc=0x139
1509         test_mkdir -p $DIR/$tdir
1510         rm -rf $DIR/$tdir/*
1511         createmany -o $DIR/$tdir/t- 1000
1512         do_nodes $list $LCTL set_param fail_loc=0
1513
1514         TLOG=$DIR/$tfile.getstripe
1515         $GETSTRIPE $DIR/$tdir > $TLOG
1516         OBJS=`awk -vobj=0 '($1 == 0) { obj += 1 } END { print obj;}' $TLOG`
1517         unlinkmany $DIR/$tdir/t- 1000
1518         [ $OBJS -gt 0 ] && \
1519                 error "$OBJS objects created on OST-0.  See $TLOG" || pass
1520 }
1521 run_test 27u "skip object creation on OSC w/o objects =========="
1522
1523 test_27v() { # bug 4900
1524         [ "$OSTCOUNT" -lt "2" ] && skip_env "too few OSTs" && return
1525         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1526         remote_mds_nodsh && skip "remote MDS with nodsh" && return
1527         remote_ost_nodsh && skip "remote OST with nodsh" && return
1528
1529         exhaust_all_precreations 0x215
1530         reset_enospc
1531
1532         test_mkdir -p $DIR/$tdir
1533         $SETSTRIPE -c 1 $DIR/$tdir         # 1 stripe / file
1534
1535         touch $DIR/$tdir/$tfile
1536         #define OBD_FAIL_TGT_DELAY_PRECREATE     0x705
1537         # all except ost1
1538         for (( i=1; i < OSTCOUNT; i++ )); do
1539                 do_facet ost$i lctl set_param fail_loc=0x705
1540         done
1541         local START=`date +%s`
1542         createmany -o $DIR/$tdir/$tfile 32
1543
1544         local FINISH=`date +%s`
1545         local TIMEOUT=`lctl get_param -n timeout`
1546         local PROCESS=$((FINISH - START))
1547         [ $PROCESS -ge $((TIMEOUT / 2)) ] && \
1548                error "$FINISH - $START >= $TIMEOUT / 2"
1549         sleep $((TIMEOUT / 2 - PROCESS))
1550         reset_enospc
1551 }
1552 run_test 27v "skip object creation on slow OST ================="
1553
1554 test_27w() { # bug 10997
1555         test_mkdir -p $DIR/$tdir || error "mkdir failed"
1556         $SETSTRIPE -S 65536 $DIR/$tdir/f0 || error "setstripe failed"
1557         [ $($GETSTRIPE -S $DIR/$tdir/f0) -ne 65536 ] &&
1558                 error "stripe size $size != 65536" || true
1559         [ $($GETSTRIPE -d $DIR/$tdir | grep -c "stripe_count") -ne 1 ] &&
1560                 error "$GETSTRIPE -d $DIR/$tdir failed" || true
1561 }
1562 run_test 27w "check $SETSTRIPE -S option"
1563
1564 test_27wa() {
1565         [ "$OSTCOUNT" -lt "2" ] &&
1566                 skip_env "skipping multiple stripe count/offset test" && return
1567
1568         test_mkdir -p $DIR/$tdir || error "mkdir failed"
1569         for i in $(seq 1 $OSTCOUNT); do
1570                 offset=$((i - 1))
1571                 $SETSTRIPE -c $i -i $offset $DIR/$tdir/f$i ||
1572                         error "setstripe -c $i -i $offset failed"
1573                 count=$($GETSTRIPE -c $DIR/$tdir/f$i)
1574                 index=$($GETSTRIPE -i $DIR/$tdir/f$i)
1575                 [ $count -ne $i ] && error "stripe count $count != $i" || true
1576                 [ $index -ne $offset ] &&
1577                         error "stripe offset $index != $offset" || true
1578         done
1579 }
1580 run_test 27wa "check $SETSTRIPE -c -i options"
1581
1582 test_27x() {
1583         remote_ost_nodsh && skip "remote OST with nodsh" && return
1584         [ "$OSTCOUNT" -lt "2" ] && skip_env "$OSTCOUNT < 2 OSTs" && return
1585         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1586         OFFSET=$(($OSTCOUNT - 1))
1587         OSTIDX=0
1588         local OST=$(ostname_from_index $OSTIDX)
1589
1590         test_mkdir -p $DIR/$tdir
1591         $SETSTRIPE -c 1 $DIR/$tdir      # 1 stripe per file
1592         do_facet ost$((OSTIDX + 1)) lctl set_param -n obdfilter.$OST.degraded 1
1593         sleep_maxage
1594         createmany -o $DIR/$tdir/$tfile $OSTCOUNT
1595         for i in `seq 0 $OFFSET`; do
1596                 [ `$GETSTRIPE $DIR/$tdir/$tfile$i | grep -A 10 obdidx | awk '{print $1}' | grep -w "$OSTIDX"` ] &&
1597                 error "OST0 was degraded but new created file still use it"
1598         done
1599         do_facet ost$((OSTIDX + 1)) lctl set_param -n obdfilter.$OST.degraded 0
1600 }
1601 run_test 27x "create files while OST0 is degraded"
1602
1603 test_27y() {
1604         [ "$OSTCOUNT" -lt "2" ] && skip_env "$OSTCOUNT < 2 OSTs -- skipping" && return
1605         remote_mds_nodsh && skip "remote MDS with nodsh" && return
1606         remote_ost_nodsh && skip "remote OST with nodsh" && return
1607         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1608
1609         local mdtosc=$(get_mdtosc_proc_path $SINGLEMDS $FSNAME-OST0000)
1610         local last_id=$(do_facet $SINGLEMDS lctl get_param -n \
1611             osc.$mdtosc.prealloc_last_id)
1612         local next_id=$(do_facet $SINGLEMDS lctl get_param -n \
1613             osc.$mdtosc.prealloc_next_id)
1614         local fcount=$((last_id - next_id))
1615         [ $fcount -eq 0 ] && skip "not enough space on OST0" && return
1616         [ $fcount -gt $OSTCOUNT ] && fcount=$OSTCOUNT
1617
1618         local MDS_OSCS=$(do_facet $SINGLEMDS lctl dl |
1619                          awk '/[oO][sS][cC].*md[ts]/ { print $4 }')
1620         local OST_DEACTIVE_IDX=-1
1621         local OSC
1622         local OSTIDX
1623         local OST
1624
1625         for OSC in $MDS_OSCS; do
1626                 OST=$(osc_to_ost $OSC)
1627                 OSTIDX=$(index_from_ostuuid $OST)
1628                 if [ $OST_DEACTIVE_IDX == -1 ]; then
1629                         OST_DEACTIVE_IDX=$OSTIDX
1630                 fi
1631                 if [ $OSTIDX != $OST_DEACTIVE_IDX ]; then
1632                         echo $OSC "is Deactivated:"
1633                         do_facet $SINGLEMDS lctl --device  %$OSC deactivate
1634                 fi
1635         done
1636
1637         OSTIDX=$(index_from_ostuuid $OST)
1638         mkdir -p $DIR/$tdir
1639         $SETSTRIPE -c 1 $DIR/$tdir      # 1 stripe / file
1640
1641         for OSC in $MDS_OSCS; do
1642                 OST=$(osc_to_ost $OSC)
1643                 OSTIDX=$(index_from_ostuuid $OST)
1644                 if [ $OSTIDX == $OST_DEACTIVE_IDX ]; then
1645                         echo $OST "is degraded:"
1646                         do_facet ost$((OSTIDX+1)) lctl set_param -n \
1647                                                 obdfilter.$OST.degraded=1
1648                 fi
1649         done
1650
1651         sleep_maxage
1652         createmany -o $DIR/$tdir/$tfile $fcount
1653
1654         for OSC in $MDS_OSCS; do
1655                 OST=$(osc_to_ost $OSC)
1656                 OSTIDX=$(index_from_ostuuid $OST)
1657                 if [ $OSTIDX == $OST_DEACTIVE_IDX ]; then
1658                         echo $OST "is recovered from degraded:"
1659                         do_facet ost$((OSTIDX+1)) lctl set_param -n \
1660                                                 obdfilter.$OST.degraded=0
1661                 else
1662                         do_facet $SINGLEMDS lctl --device %$OSC activate
1663                 fi
1664         done
1665
1666         # all osp devices get activated, hence -1 stripe count restored
1667         local stripecnt=0
1668
1669         # sleep 2*lod_qos_maxage seconds waiting for lod qos to notice osp
1670         # devices get activated.
1671         sleep_maxage
1672         $SETSTRIPE -c -1 $DIR/$tfile
1673         stripecnt=$($GETSTRIPE -c $DIR/$tfile)
1674         rm -f $DIR/$tfile
1675         [ $stripecnt -ne $OSTCOUNT ] &&
1676                 error "Of $OSTCOUNT OSTs, only $stripecnt is available"
1677         return 0
1678 }
1679 run_test 27y "create files while OST0 is degraded and the rest inactive"
1680
1681 check_seq_oid()
1682 {
1683         log "check file $1"
1684
1685         lmm_count=$($GETSTRIPE -c $1)
1686         lmm_seq=$($GETSTRIPE -v $1 | awk '/lmm_seq/ { print $2 }')
1687         lmm_oid=$($GETSTRIPE -v $1 | awk '/lmm_object_id/ { print $2 }')
1688
1689         local old_ifs="$IFS"
1690         IFS=$'[:]'
1691         fid=($($LFS path2fid $1))
1692         IFS="$old_ifs"
1693
1694         log "FID seq ${fid[1]}, oid ${fid[2]} ver ${fid[3]}"
1695         log "LOV seq $lmm_seq, oid $lmm_oid, count: $lmm_count"
1696
1697         # compare lmm_seq and lu_fid->f_seq
1698         [ $lmm_seq = ${fid[1]} ] || { error "SEQ mismatch"; return 1; }
1699         # compare lmm_object_id and lu_fid->oid
1700         [ $lmm_oid = ${fid[2]} ] || { error "OID mismatch"; return 2; }
1701
1702         # check the trusted.fid attribute of the OST objects of the file
1703         local have_obdidx=false
1704         local stripe_nr=0
1705         $GETSTRIPE $1 | while read obdidx oid hex seq; do
1706                 # skip lines up to and including "obdidx"
1707                 [ -z "$obdidx" ] && break
1708                 [ "$obdidx" = "obdidx" ] && have_obdidx=true && continue
1709                 $have_obdidx || continue
1710
1711                 local ost=$((obdidx + 1))
1712                 local dev=$(ostdevname $ost)
1713                 local oid_hex
1714
1715                 if [ $(facet_fstype ost$ost) != ldiskfs ]; then
1716                         echo "Currently only works with ldiskfs-based OSTs"
1717                         continue
1718                 fi
1719
1720                 log "want: stripe:$stripe_nr ost:$obdidx oid:$oid/$hex seq:$seq"
1721
1722                 #don't unmount/remount the OSTs if we don't need to do that
1723                 # LU-2577 changes filter_fid to be smaller, so debugfs needs
1724                 # update too, until that use mount/ll_decode_filter_fid/mount
1725                 local dir=$(facet_mntpt ost$ost)
1726                 local opts=${OST_MOUNT_OPTS}
1727
1728                 if !  do_facet ost$ost test -b ${dev}; then
1729                         opts=$(csa_add "$opts" -o loop)
1730                 fi
1731
1732                 stop ost$ost
1733                 do_facet ost$ost mount -t $(facet_fstype ost$ost) $opts $dev $dir ||
1734                         { error "mounting $dev as $FSTYPE failed"; return 3; }
1735
1736                 seq=$(echo $seq | sed -e "s/^0x//g")
1737                 if [ $seq == 0 ]; then
1738                         oid_hex=$(echo $oid)
1739                 else
1740                         oid_hex=$(echo $hex | sed -e "s/^0x//g")
1741                 fi
1742                 local obj_file=$(do_facet ost$ost find $dir/O/$seq -name $oid_hex)
1743                 local ff=$(do_facet ost$ost $LL_DECODE_FILTER_FID $obj_file)
1744                 do_facet ost$ost umount -d $dir
1745                 start ost$ost $dev $OST_MOUNT_OPTS
1746
1747                 # re-enable when debugfs will understand new filter_fid
1748                 #local ff=$(do_facet ost$ost "$DEBUGFS -c -R 'stat $obj_file' \
1749                 #           $dev 2>/dev/null" | grep "parent=")
1750
1751                 [ -z "$ff" ] && error "$obj_file: no filter_fid info"
1752
1753                 echo "$ff" | sed -e 's#.*objid=#got: objid=#'
1754
1755                 # /mnt/O/0/d23/23: objid=23 seq=0 parent=[0x200000400:0x1e:0x1]
1756                 # fid: objid=23 seq=0 parent=[0x200000400:0x1e:0x0] stripe=1
1757                 local ff_parent=$(echo $ff|sed -e 's/.*parent=.//')
1758                 local ff_pseq=$(echo $ff_parent | cut -d: -f1)
1759                 local ff_poid=$(echo $ff_parent | cut -d: -f2)
1760                 local ff_pstripe=$(echo $ff_parent | sed -e 's/.*stripe=//')
1761
1762                 # compare lmm_seq and filter_fid->ff_parent.f_seq
1763                 [ $ff_pseq = $lmm_seq ] ||
1764                         error "FF parent SEQ $ff_pseq != $lmm_seq"
1765                 # compare lmm_object_id and filter_fid->ff_parent.f_oid
1766                 [ $ff_poid = $lmm_oid ] ||
1767                         error "FF parent OID $ff_poid != $lmm_oid"
1768                 [ $ff_pstripe = $stripe_nr ] ||
1769                         error "FF stripe $ff_pstripe != $stripe_nr"
1770
1771                 stripe_nr=$((stripe_nr + 1))
1772         done
1773 }
1774
1775 test_27z() {
1776         remote_ost_nodsh && skip "remote OST with nodsh" && return
1777         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1778         test_mkdir -p $DIR/$tdir
1779
1780         $SETSTRIPE -c 1 -i 0 -S 64k $DIR/$tdir/$tfile-1 ||
1781                 { error "setstripe -c -1 failed"; return 1; }
1782         # We need to send a write to every object to get parent FID info set.
1783         # This _should_ also work for setattr, but does not currently.
1784         # touch $DIR/$tdir/$tfile-1 ||
1785         dd if=/dev/zero of=$DIR/$tdir/$tfile-1 bs=1M count=1 ||
1786                 { error "dd $tfile-1 failed"; return 2; }
1787         $SETSTRIPE -c -1 -i $((OSTCOUNT - 1)) -S 1M $DIR/$tdir/$tfile-2 ||
1788                 { error "setstripe -c -1 failed"; return 3; }
1789         dd if=/dev/zero of=$DIR/$tdir/$tfile-2 bs=1M count=$OSTCOUNT ||
1790                 { error "dd $tfile-2 failed"; return 4; }
1791
1792         # make sure write RPCs have been sent to OSTs
1793         sync; sleep 5; sync
1794
1795         check_seq_oid $DIR/$tdir/$tfile-1 || return 5
1796         check_seq_oid $DIR/$tdir/$tfile-2 || return 6
1797 }
1798 run_test 27z "check SEQ/OID on the MDT and OST filesystems"
1799
1800 test_27A() { # b=19102
1801         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1802         local restore_size=$($GETSTRIPE -S $MOUNT)
1803         local restore_count=$($GETSTRIPE -c $MOUNT)
1804         local restore_offset=$($GETSTRIPE -i $MOUNT)
1805         $SETSTRIPE -c 0 -i -1 -S 0 $MOUNT
1806         local default_size=$($GETSTRIPE -S $MOUNT)
1807         local default_count=$($GETSTRIPE -c $MOUNT)
1808         local default_offset=$($GETSTRIPE -i $MOUNT)
1809         local dsize=$((1024 * 1024))
1810         [ $default_size -eq $dsize ] ||
1811                 error "stripe size $default_size != $dsize"
1812         [ $default_count -eq 1 ] || error "stripe count $default_count != 1"
1813         [ $default_offset -eq -1 ] ||error "stripe offset $default_offset != -1"
1814         $SETSTRIPE -c $restore_count -i $restore_offset -S $restore_size $MOUNT
1815 }
1816 run_test 27A "check filesystem-wide default LOV EA values"
1817
1818 test_27B() { # LU-2523
1819         test_mkdir -p $DIR/$tdir
1820         rm -f $DIR/$tdir/f0 $DIR/$tdir/f1
1821         touch $DIR/$tdir/f0
1822         # open f1 with O_LOV_DELAY_CREATE
1823         # rename f0 onto f1
1824         # call setstripe ioctl on open file descriptor for f1
1825         # close
1826         multiop $DIR/$tdir/f1 oO_RDWR:O_CREAT:O_LOV_DELAY_CREATE:nB1c \
1827                 $DIR/$tdir/f0
1828
1829         rm -f $DIR/$tdir/f1
1830         # open f1 with O_LOV_DELAY_CREATE
1831         # unlink f1
1832         # call setstripe ioctl on open file descriptor for f1
1833         # close
1834         multiop $DIR/$tdir/f1 oO_RDWR:O_CREAT:O_LOV_DELAY_CREATE:uB1c
1835
1836         # Allow multiop to fail in imitation of NFS's busted semantics.
1837         true
1838 }
1839 run_test 27B "call setstripe on open unlinked file/rename victim"
1840
1841 test_27C() { #LU-2871
1842         [ $OSTCOUNT -lt 2 ] && skip "needs >= 2 OSTs" && return
1843
1844         declare -a ost_idx
1845         local index
1846         local i
1847         local j
1848
1849         test_mkdir -p $DIR/$tdir
1850         cd $DIR/$tdir
1851         for i in $(seq 0 $((OSTCOUNT - 1))); do
1852                 # set stripe across all OSTs starting from OST$i
1853                 $SETSTRIPE -i $i -c -1 $tfile$i
1854                 # get striping information
1855                 ost_idx=($($GETSTRIPE $tfile$i |
1856                          tail -n $((OSTCOUNT + 1)) | awk '{print $1}'))
1857                 echo ${ost_idx[@]}
1858                 # check the layout
1859                 for j in $(seq 0 $((OSTCOUNT - 1))); do
1860                         index=$(((i + j) % OSTCOUNT))
1861                         [ ${ost_idx[$j]} -eq $index ] ||
1862                                 error "$j:${ost_idx[$j]} != $index"
1863                 done
1864         done
1865 }
1866 run_test 27C "check full striping across all OSTs"
1867
1868 # createtest also checks that device nodes are created and
1869 # then visible correctly (#2091)
1870 test_28() { # bug 2091
1871         test_mkdir $DIR/d28
1872         $CREATETEST $DIR/d28/ct || error
1873 }
1874 run_test 28 "create/mknod/mkdir with bad file types ============"
1875
1876 test_29() {
1877         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1878         cancel_lru_locks mdc
1879         test_mkdir $DIR/d29
1880         touch $DIR/d29/foo
1881         log 'first d29'
1882         ls -l $DIR/d29
1883
1884         declare -i LOCKCOUNTORIG=0
1885         for lock_count in $(lctl get_param -n ldlm.namespaces.*mdc*.lock_count); do
1886                 let LOCKCOUNTORIG=$LOCKCOUNTORIG+$lock_count
1887         done
1888         [ $LOCKCOUNTORIG -eq 0 ] && echo "No mdc lock count" && return 1
1889
1890         declare -i LOCKUNUSEDCOUNTORIG=0
1891         for unused_count in $(lctl get_param -n ldlm.namespaces.*mdc*.lock_unused_count); do
1892                 let LOCKUNUSEDCOUNTORIG=$LOCKUNUSEDCOUNTORIG+$unused_count
1893         done
1894
1895         log 'second d29'
1896         ls -l $DIR/d29
1897         log 'done'
1898
1899         declare -i LOCKCOUNTCURRENT=0
1900         for lock_count in $(lctl get_param -n ldlm.namespaces.*mdc*.lock_count); do
1901                 let LOCKCOUNTCURRENT=$LOCKCOUNTCURRENT+$lock_count
1902         done
1903
1904         declare -i LOCKUNUSEDCOUNTCURRENT=0
1905         for unused_count in $(lctl get_param -n ldlm.namespaces.*mdc*.lock_unused_count); do
1906                 let LOCKUNUSEDCOUNTCURRENT=$LOCKUNUSEDCOUNTCURRENT+$unused_count
1907         done
1908
1909         if [ "$LOCKCOUNTCURRENT" -gt "$LOCKCOUNTORIG" ]; then
1910                 lctl set_param -n ldlm.dump_namespaces ""
1911                 error "CURRENT: $LOCKCOUNTCURRENT > $LOCKCOUNTORIG"
1912                 $LCTL dk | sort -k4 -t: > $TMP/test_29.dk
1913                 log "dumped log to $TMP/test_29.dk (bug 5793)"
1914                 return 2
1915         fi
1916         if [ "$LOCKUNUSEDCOUNTCURRENT" -gt "$LOCKUNUSEDCOUNTORIG" ]; then
1917                 error "UNUSED: $LOCKUNUSEDCOUNTCURRENT > $LOCKUNUSEDCOUNTORIG"
1918                 $LCTL dk | sort -k4 -t: > $TMP/test_29.dk
1919                 log "dumped log to $TMP/test_29.dk (bug 5793)"
1920                 return 3
1921         fi
1922 }
1923 run_test 29 "IT_GETATTR regression  ============================"
1924
1925 test_30a() { # was test_30
1926         cp `which ls` $DIR || cp /bin/ls $DIR
1927         $DIR/ls / || error
1928         rm $DIR/ls
1929 }
1930 run_test 30a "execute binary from Lustre (execve) =============="
1931
1932 test_30b() {
1933         cp `which ls` $DIR || cp /bin/ls $DIR
1934         chmod go+rx $DIR/ls
1935         $RUNAS $DIR/ls / || error
1936         rm $DIR/ls
1937 }
1938 run_test 30b "execute binary from Lustre as non-root ==========="
1939
1940 test_30c() { # b=22376
1941         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1942         cp `which ls` $DIR || cp /bin/ls $DIR
1943         chmod a-rw $DIR/ls
1944         cancel_lru_locks mdc
1945         cancel_lru_locks osc
1946         $RUNAS $DIR/ls / || error
1947         rm -f $DIR/ls
1948 }
1949 run_test 30c "execute binary from Lustre without read perms ===="
1950
1951 test_31a() {
1952         $OPENUNLINK $DIR/f31 $DIR/f31 || error
1953         $CHECKSTAT -a $DIR/f31 || error
1954 }
1955 run_test 31a "open-unlink file =================================="
1956
1957 test_31b() {
1958         touch $DIR/f31 || error
1959         ln $DIR/f31 $DIR/f31b || error
1960         $MULTIOP $DIR/f31b Ouc || error
1961         $CHECKSTAT -t file $DIR/f31 || error
1962 }
1963 run_test 31b "unlink file with multiple links while open ======="
1964
1965 test_31c() {
1966         touch $DIR/f31 || error
1967         ln $DIR/f31 $DIR/f31c || error
1968         multiop_bg_pause $DIR/f31 O_uc || return 1
1969         MULTIPID=$!
1970         $MULTIOP $DIR/f31c Ouc
1971         kill -USR1 $MULTIPID
1972         wait $MULTIPID
1973 }
1974 run_test 31c "open-unlink file with multiple links ============="
1975
1976 test_31d() {
1977         opendirunlink $DIR/d31d $DIR/d31d || error
1978         $CHECKSTAT -a $DIR/d31d || error
1979 }
1980 run_test 31d "remove of open directory ========================="
1981
1982 test_31e() { # bug 2904
1983         check_kernel_version 34 || return 0
1984         openfilleddirunlink $DIR/d31e || error
1985 }
1986 run_test 31e "remove of open non-empty directory ==============="
1987
1988 test_31f() { # bug 4554
1989         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
1990         set -vx
1991         test_mkdir $DIR/d31f
1992         $SETSTRIPE -S 1048576 -c 1 $DIR/d31f
1993         cp /etc/hosts $DIR/d31f
1994         ls -l $DIR/d31f
1995         $GETSTRIPE $DIR/d31f/hosts
1996         multiop_bg_pause $DIR/d31f D_c || return 1
1997         MULTIPID=$!
1998
1999         rm -rv $DIR/d31f || error "first of $DIR/d31f"
2000         test_mkdir $DIR/d31f
2001         $SETSTRIPE -S 1048576 -c 1 $DIR/d31f
2002         cp /etc/hosts $DIR/d31f
2003         ls -l $DIR/d31f
2004         $GETSTRIPE $DIR/d31f/hosts
2005         multiop_bg_pause $DIR/d31f D_c || return 1
2006         MULTIPID2=$!
2007
2008         kill -USR1 $MULTIPID || error "first opendir $MULTIPID not running"
2009         wait $MULTIPID || error "first opendir $MULTIPID failed"
2010
2011         sleep 6
2012
2013         kill -USR1 $MULTIPID2 || error "second opendir $MULTIPID not running"
2014         wait $MULTIPID2 || error "second opendir $MULTIPID2 failed"
2015         set +vx
2016 }
2017 run_test 31f "remove of open directory with open-unlink file ==="
2018
2019 test_31g() {
2020         echo "-- cross directory link --"
2021         test_mkdir $DIR/d31ga
2022         test_mkdir $DIR/d31gb
2023         touch $DIR/d31ga/f
2024         ln $DIR/d31ga/f $DIR/d31gb/g
2025         $CHECKSTAT -t file $DIR/d31ga/f || error "source"
2026         [ `stat -c%h $DIR/d31ga/f` == '2' ] || error "source nlink"
2027         $CHECKSTAT -t file $DIR/d31gb/g || error "target"
2028         [ `stat -c%h $DIR/d31gb/g` == '2' ] || error "target nlink"
2029 }
2030 run_test 31g "cross directory link==============="
2031
2032 test_31h() {
2033         echo "-- cross directory link --"
2034         test_mkdir $DIR/d31h
2035         test_mkdir $DIR/d31h/dir
2036         touch $DIR/d31h/f
2037         ln $DIR/d31h/f $DIR/d31h/dir/g
2038         $CHECKSTAT -t file $DIR/d31h/f || error "source"
2039         [ `stat -c%h $DIR/d31h/f` == '2' ] || error "source nlink"
2040         $CHECKSTAT -t file $DIR/d31h/dir/g || error "target"
2041         [ `stat -c%h $DIR/d31h/dir/g` == '2' ] || error "target nlink"
2042 }
2043 run_test 31h "cross directory link under child==============="
2044
2045 test_31i() {
2046         echo "-- cross directory link --"
2047         test_mkdir $DIR/d31i
2048         test_mkdir $DIR/d31i/dir
2049         touch $DIR/d31i/dir/f
2050         ln $DIR/d31i/dir/f $DIR/d31i/g
2051         $CHECKSTAT -t file $DIR/d31i/dir/f || error "source"
2052         [ `stat -c%h $DIR/d31i/dir/f` == '2' ] || error "source nlink"
2053         $CHECKSTAT -t file $DIR/d31i/g || error "target"
2054         [ `stat -c%h $DIR/d31i/g` == '2' ] || error "target nlink"
2055 }
2056 run_test 31i "cross directory link under parent==============="
2057
2058
2059 test_31j() {
2060         test_mkdir $DIR/d31j
2061         test_mkdir $DIR/d31j/dir1
2062         ln $DIR/d31j/dir1 $DIR/d31j/dir2 && error "ln for dir"
2063         link $DIR/d31j/dir1 $DIR/d31j/dir3 && error "link for dir"
2064         mlink $DIR/d31j/dir1 $DIR/d31j/dir4 && error "mlink for dir"
2065         mlink $DIR/d31j/dir1 $DIR/d31j/dir1 && error "mlink to the same dir"
2066         return 0
2067 }
2068 run_test 31j "link for directory==============="
2069
2070
2071 test_31k() {
2072         test_mkdir $DIR/d31k
2073         touch $DIR/d31k/s
2074         touch $DIR/d31k/exist
2075         mlink $DIR/d31k/s $DIR/d31k/t || error "mlink"
2076         mlink $DIR/d31k/s $DIR/d31k/exist && error "mlink to exist file"
2077         mlink $DIR/d31k/s $DIR/d31k/s && error "mlink to the same file"
2078         mlink $DIR/d31k/s $DIR/d31k && error "mlink to parent dir"
2079         mlink $DIR/d31k $DIR/d31k/s && error "mlink parent dir to target"
2080         mlink $DIR/d31k/not-exist $DIR/d31k/foo && error "mlink non-existing to new"
2081         mlink $DIR/d31k/not-exist $DIR/d31k/s && error "mlink non-existing to exist"
2082         return 0
2083 }
2084 run_test 31k "link to file: the same, non-existing, dir==============="
2085
2086 test_31m() {
2087         test_mkdir $DIR/d31m
2088         touch $DIR/d31m/s
2089         test_mkdir $DIR/d31m2
2090         touch $DIR/d31m2/exist
2091         mlink $DIR/d31m/s $DIR/d31m2/t || error "mlink"
2092         mlink $DIR/d31m/s $DIR/d31m2/exist && error "mlink to exist file"
2093         mlink $DIR/d31m/s $DIR/d31m2 && error "mlink to parent dir"
2094         mlink $DIR/d31m2 $DIR/d31m/s && error "mlink parent dir to target"
2095         mlink $DIR/d31m/not-exist $DIR/d31m2/foo && error "mlink non-existing to new"
2096         mlink $DIR/d31m/not-exist $DIR/d31m2/s && error "mlink non-existing to exist"
2097         return 0
2098 }
2099 run_test 31m "link to file: the same, non-existing, dir==============="
2100
2101 test_31n() {
2102         [ -e /proc/self/fd/173 ] && echo "skipping, fd 173 is in use" && return
2103         touch $DIR/$tfile || error "cannot create '$DIR/$tfile'"
2104         nlink=$(stat --format=%h $DIR/$tfile)
2105         [ ${nlink:--1} -eq 1 ] || error "nlink is $nlink, expected 1"
2106         exec 173<$DIR/$tfile
2107         trap "exec 173<&-" EXIT
2108         nlink=$(stat --dereference --format=%h /proc/self/fd/173)
2109         [ ${nlink:--1} -eq 1 ] || error "nlink is $nlink, expected 1"
2110         rm $DIR/$tfile || error "cannot remove '$DIR/$tfile'"
2111         nlink=$(stat --dereference --format=%h /proc/self/fd/173)
2112         [ ${nlink:--1} -eq 0 ] || error "nlink is $nlink, expected 0"
2113         exec 173<&-
2114 }
2115 run_test 31n "check link count of unlinked file"
2116
2117 cleanup_test32_mount() {
2118         trap 0
2119         $UMOUNT $DIR/$tdir/ext2-mountpoint
2120 }
2121
2122 test_32a() {
2123         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2124         echo "== more mountpoints and symlinks ================="
2125         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
2126         trap cleanup_test32_mount EXIT
2127         test_mkdir -p $DIR/$tdir/ext2-mountpoint
2128         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint || error
2129         $CHECKSTAT -t dir $DIR/$tdir/ext2-mountpoint/.. || error
2130         cleanup_test32_mount
2131 }
2132 run_test 32a "stat d32a/ext2-mountpoint/.. ====================="
2133
2134 test_32b() {
2135         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2136         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
2137         trap cleanup_test32_mount EXIT
2138         test_mkdir -p $DIR/$tdir/ext2-mountpoint
2139         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint || error
2140         ls -al $DIR/$tdir/ext2-mountpoint/.. || error
2141         cleanup_test32_mount
2142 }
2143 run_test 32b "open d32b/ext2-mountpoint/.. ====================="
2144
2145 test_32c() {
2146         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2147         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
2148         trap cleanup_test32_mount EXIT
2149         test_mkdir -p $DIR/$tdir/ext2-mountpoint
2150         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint || error
2151         test_mkdir -p $DIR/$tdir/d2/test_dir
2152         $CHECKSTAT -t dir $DIR/$tdir/ext2-mountpoint/../d2/test_dir || error
2153         cleanup_test32_mount
2154 }
2155 run_test 32c "stat d32c/ext2-mountpoint/../d2/test_dir ========="
2156
2157 test_32d() {
2158         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2159         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
2160         trap cleanup_test32_mount EXIT
2161         test_mkdir -p $DIR/$tdir/ext2-mountpoint
2162         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint || error
2163         test_mkdir -p $DIR/$tdir/d2/test_dir
2164         ls -al $DIR/$tdir/ext2-mountpoint/../d2/test_dir || error
2165         cleanup_test32_mount
2166 }
2167 run_test 32d "open d32d/ext2-mountpoint/../d2/test_dir ========="
2168
2169 test_32e() {
2170         [ -e $DIR/d32e ] && rm -fr $DIR/d32e
2171         test_mkdir -p $DIR/d32e/tmp
2172         TMP_DIR=$DIR/d32e/tmp
2173         ln -s $DIR/d32e $TMP_DIR/symlink11
2174         ln -s $TMP_DIR/symlink11 $TMP_DIR/../symlink01
2175         $CHECKSTAT -t link $DIR/d32e/tmp/symlink11 || error
2176         $CHECKSTAT -t link $DIR/d32e/symlink01 || error
2177 }
2178 run_test 32e "stat d32e/symlink->tmp/symlink->lustre-subdir ===="
2179
2180 test_32f() {
2181         [ -e $DIR/d32f ] && rm -fr $DIR/d32f
2182         test_mkdir -p $DIR/d32f/tmp
2183         TMP_DIR=$DIR/d32f/tmp
2184         ln -s $DIR/d32f $TMP_DIR/symlink11
2185         ln -s $TMP_DIR/symlink11 $TMP_DIR/../symlink01
2186         ls $DIR/d32f/tmp/symlink11  || error
2187         ls $DIR/d32f/symlink01 || error
2188 }
2189 run_test 32f "open d32f/symlink->tmp/symlink->lustre-subdir ===="
2190
2191 test_32g() {
2192         TMP_DIR=$DIR/$tdir/tmp
2193         test_mkdir -p $DIR/$tdir/tmp
2194         test_mkdir $DIR/${tdir}2
2195         ln -s $DIR/${tdir}2 $TMP_DIR/symlink12
2196         ln -s $TMP_DIR/symlink12 $TMP_DIR/../symlink02
2197         $CHECKSTAT -t link $TMP_DIR/symlink12 || error
2198         $CHECKSTAT -t link $DIR/$tdir/symlink02 || error
2199         $CHECKSTAT -t dir -f $TMP_DIR/symlink12 || error
2200         $CHECKSTAT -t dir -f $DIR/$tdir/symlink02 || error
2201 }
2202 run_test 32g "stat d32g/symlink->tmp/symlink->lustre-subdir/${tdir}2"
2203
2204 test_32h() {
2205         rm -fr $DIR/$tdir $DIR/${tdir}2
2206         TMP_DIR=$DIR/$tdir/tmp
2207         test_mkdir -p $DIR/$tdir/tmp
2208         test_mkdir $DIR/${tdir}2
2209         ln -s $DIR/${tdir}2 $TMP_DIR/symlink12
2210         ln -s $TMP_DIR/symlink12 $TMP_DIR/../symlink02
2211         ls $TMP_DIR/symlink12 || error
2212         ls $DIR/$tdir/symlink02  || error
2213 }
2214 run_test 32h "open d32h/symlink->tmp/symlink->lustre-subdir/${tdir}2"
2215
2216 test_32i() {
2217         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2218         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
2219         trap cleanup_test32_mount EXIT
2220         test_mkdir -p $DIR/$tdir/ext2-mountpoint
2221         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint || error
2222         touch $DIR/$tdir/test_file
2223         $CHECKSTAT -t file $DIR/$tdir/ext2-mountpoint/../test_file || error
2224         cleanup_test32_mount
2225 }
2226 run_test 32i "stat d32i/ext2-mountpoint/../test_file ==========="
2227
2228 test_32j() {
2229         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2230         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
2231         trap cleanup_test32_mount EXIT
2232         test_mkdir -p $DIR/$tdir/ext2-mountpoint
2233         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint || error
2234         touch $DIR/$tdir/test_file
2235         cat $DIR/$tdir/ext2-mountpoint/../test_file || error
2236         cleanup_test32_mount
2237 }
2238 run_test 32j "open d32j/ext2-mountpoint/../test_file ==========="
2239
2240 test_32k() {
2241         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2242         rm -fr $DIR/$tdir
2243         trap cleanup_test32_mount EXIT
2244         test_mkdir -p $DIR/$tdir/ext2-mountpoint
2245         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint
2246         test_mkdir -p $DIR/$tdir/d2
2247         touch $DIR/$tdir/d2/test_file || error
2248         $CHECKSTAT -t file $DIR/$tdir/ext2-mountpoint/../d2/test_file || error
2249         cleanup_test32_mount
2250 }
2251 run_test 32k "stat d32k/ext2-mountpoint/../d2/test_file ========"
2252
2253 test_32l() {
2254         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2255         rm -fr $DIR/$tdir
2256         trap cleanup_test32_mount EXIT
2257         test_mkdir -p $DIR/$tdir/ext2-mountpoint
2258         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir/ext2-mountpoint || error
2259         test_mkdir -p $DIR/$tdir/d2
2260         touch $DIR/$tdir/d2/test_file
2261         cat  $DIR/$tdir/ext2-mountpoint/../d2/test_file || error
2262         cleanup_test32_mount
2263 }
2264 run_test 32l "open d32l/ext2-mountpoint/../d2/test_file ========"
2265
2266 test_32m() {
2267         rm -fr $DIR/d32m
2268         test_mkdir -p $DIR/d32m/tmp
2269         TMP_DIR=$DIR/d32m/tmp
2270         ln -s $DIR $TMP_DIR/symlink11
2271         ln -s $TMP_DIR/symlink11 $TMP_DIR/../symlink01
2272         $CHECKSTAT -t link $DIR/d32m/tmp/symlink11 || error
2273         $CHECKSTAT -t link $DIR/d32m/symlink01 || error
2274 }
2275 run_test 32m "stat d32m/symlink->tmp/symlink->lustre-root ======"
2276
2277 test_32n() {
2278         rm -fr $DIR/d32n
2279         test_mkdir -p $DIR/d32n/tmp
2280         TMP_DIR=$DIR/d32n/tmp
2281         ln -s $DIR $TMP_DIR/symlink11
2282         ln -s $TMP_DIR/symlink11 $TMP_DIR/../symlink01
2283         ls -l $DIR/d32n/tmp/symlink11  || error
2284         ls -l $DIR/d32n/symlink01 || error
2285 }
2286 run_test 32n "open d32n/symlink->tmp/symlink->lustre-root ======"
2287
2288 test_32o() {
2289         rm -fr $DIR/d32o $DIR/$tfile
2290         touch $DIR/$tfile
2291         test_mkdir -p $DIR/d32o/tmp
2292         TMP_DIR=$DIR/d32o/tmp
2293         ln -s $DIR/$tfile $TMP_DIR/symlink12
2294         ln -s $TMP_DIR/symlink12 $TMP_DIR/../symlink02
2295         $CHECKSTAT -t link $DIR/d32o/tmp/symlink12 || error
2296         $CHECKSTAT -t link $DIR/d32o/symlink02 || error
2297         $CHECKSTAT -t file -f $DIR/d32o/tmp/symlink12 || error
2298         $CHECKSTAT -t file -f $DIR/d32o/symlink02 || error
2299 }
2300 run_test 32o "stat d32o/symlink->tmp/symlink->lustre-root/$tfile"
2301
2302 test_32p() {
2303     log 32p_1
2304         rm -fr $DIR/d32p
2305     log 32p_2
2306         rm -f $DIR/$tfile
2307     log 32p_3
2308         touch $DIR/$tfile
2309     log 32p_4
2310         test_mkdir -p $DIR/d32p/tmp
2311     log 32p_5
2312         TMP_DIR=$DIR/d32p/tmp
2313     log 32p_6
2314         ln -s $DIR/$tfile $TMP_DIR/symlink12
2315     log 32p_7
2316         ln -s $TMP_DIR/symlink12 $TMP_DIR/../symlink02
2317     log 32p_8
2318         cat $DIR/d32p/tmp/symlink12 || error
2319     log 32p_9
2320         cat $DIR/d32p/symlink02 || error
2321     log 32p_10
2322 }
2323 run_test 32p "open d32p/symlink->tmp/symlink->lustre-root/$tfile"
2324
2325 cleanup_testdir_mount() {
2326         trap 0
2327         $UMOUNT $DIR/$tdir
2328 }
2329
2330 test_32q() {
2331         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2332         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
2333         trap cleanup_testdir_mount EXIT
2334         test_mkdir -p $DIR/$tdir
2335         touch $DIR/$tdir/under_the_mount
2336         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir
2337         ls $DIR/$tdir | grep "\<under_the_mount\>" && error
2338         cleanup_testdir_mount
2339 }
2340 run_test 32q "stat follows mountpoints in Lustre (should return error)"
2341
2342 test_32r() {
2343         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2344         [ -e $DIR/$tdir ] && rm -fr $DIR/$tdir
2345         trap cleanup_testdir_mount EXIT
2346         test_mkdir -p $DIR/$tdir
2347         touch $DIR/$tdir/under_the_mount
2348         mount -t ext2 -o loop $EXT2_DEV $DIR/$tdir
2349         ls $DIR/$tdir | grep -q under_the_mount && error || true
2350         cleanup_testdir_mount
2351 }
2352 run_test 32r "opendir follows mountpoints in Lustre (should return error)"
2353
2354 test_33aa() {
2355         rm -f $DIR/$tfile
2356         touch $DIR/$tfile
2357         chmod 444 $DIR/$tfile
2358         chown $RUNAS_ID $DIR/$tfile
2359         log 33_1
2360         $RUNAS $OPENFILE -f O_RDWR $DIR/$tfile && error || true
2361         log 33_2
2362 }
2363 run_test 33aa "write file with mode 444 (should return error) ===="
2364
2365 test_33a() {
2366         rm -fr $DIR/d33
2367         test_mkdir -p $DIR/d33
2368         chown $RUNAS_ID $DIR/d33
2369         $RUNAS $OPENFILE -f O_RDWR:O_CREAT -m 0444 $DIR/d33/f33|| error "create"
2370         $RUNAS $OPENFILE -f O_RDWR:O_CREAT -m 0444 $DIR/d33/f33 && \
2371                 error "open RDWR" || true
2372 }
2373 run_test 33a "test open file(mode=0444) with O_RDWR (should return error)"
2374
2375 test_33b() {
2376         rm -fr $DIR/d33
2377         test_mkdir -p $DIR/d33
2378         chown $RUNAS_ID $DIR/d33
2379         $RUNAS $OPENFILE -f 1286739555 $DIR/d33/f33 && error "create" || true
2380 }
2381 run_test 33b "test open file with malformed flags (No panic and return error)"
2382
2383 test_33c() {
2384         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2385         local ostnum
2386         local ostname
2387         local write_bytes
2388         local all_zeros
2389
2390         remote_ost_nodsh && skip "remote OST with nodsh" && return
2391         all_zeros=:
2392         rm -fr $DIR/d33
2393         test_mkdir -p $DIR/d33
2394         # Read: 0, Write: 4, create/destroy: 2/0, stat: 1, punch: 0
2395
2396         sync
2397         for ostnum in $(seq $OSTCOUNT); do
2398                 # test-framework's OST numbering is one-based, while Lustre's
2399                 # is zero-based
2400                 ostname=$(printf "$FSNAME-OST%.4d" $((ostnum - 1)))
2401                 # Parsing llobdstat's output sucks; we could grep the /proc
2402                 # path, but that's likely to not be as portable as using the
2403                 # llobdstat utility.  So we parse lctl output instead.
2404                 write_bytes=$(do_facet ost$ostnum lctl get_param -n \
2405                         obdfilter/$ostname/stats |
2406                         awk '/^write_bytes/ {print $7}' )
2407                 echo "baseline_write_bytes@$OSTnum/$ostname=$write_bytes"
2408                 if (( ${write_bytes:-0} > 0 ))
2409                 then
2410                         all_zeros=false
2411                         break;
2412                 fi
2413         done
2414
2415         $all_zeros || return 0
2416
2417         # Write four bytes
2418         echo foo > $DIR/d33/bar
2419         # Really write them
2420         sync
2421
2422         # Total up write_bytes after writing.  We'd better find non-zeros.
2423         for ostnum in $(seq $OSTCOUNT); do
2424                 ostname=$(printf "$FSNAME-OST%.4d" $((ostnum - 1)))
2425                 write_bytes=$(do_facet ost$ostnum lctl get_param -n \
2426                         obdfilter/$ostname/stats |
2427                         awk '/^write_bytes/ {print $7}' )
2428                 echo "write_bytes@$OSTnum/$ostname=$write_bytes"
2429                 if (( ${write_bytes:-0} > 0 ))
2430                 then
2431                         all_zeros=false
2432                         break;
2433                 fi
2434         done
2435
2436         if $all_zeros
2437         then
2438                 for ostnum in $(seq $OSTCOUNT); do
2439                         ostname=$(printf "$FSNAME-OST%.4d" $((ostnum - 1)))
2440                         echo "Check that write_bytes is present in obdfilter/*/stats:"
2441                         do_facet ost$ostnum lctl get_param -n \
2442                                 obdfilter/$ostname/stats
2443                 done
2444                 error "OST not keeping write_bytes stats (b22312)"
2445         fi
2446 }
2447 run_test 33c "test llobdstat and write_bytes"
2448
2449 test_33d() {
2450         [ $MDSCOUNT -lt 2 ] && skip "needs >= 2 MDTs" && return
2451         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2452         local MDTIDX=1
2453         local remote_dir=$DIR/$tdir/remote_dir
2454
2455         mkdir -p $DIR/$tdir
2456         $LFS mkdir -i $MDTIDX $remote_dir ||
2457                 error "create remote directory failed"
2458
2459         touch $remote_dir/$tfile
2460         chmod 444 $remote_dir/$tfile
2461         chown $RUNAS_ID $remote_dir/$tfile
2462
2463         $RUNAS $OPENFILE -f O_RDWR $DIR/$tfile && error || true
2464
2465         chown $RUNAS_ID $remote_dir
2466         $RUNAS $OPENFILE -f O_RDWR:O_CREAT -m 0444 $remote_dir/f33 ||
2467                                         error "create" || true
2468         $RUNAS $OPENFILE -f O_RDWR:O_CREAT -m 0444 $remote_dir/f33 &&
2469                                     error "open RDWR" || true
2470         $RUNAS $OPENFILE -f 1286739555 $remote_dir/f33 &&
2471                                     error "create" || true
2472 }
2473 run_test 33d "openfile with 444 modes and malformed flags under remote dir"
2474
2475 TEST_34_SIZE=${TEST_34_SIZE:-2000000000000}
2476 test_34a() {
2477         rm -f $DIR/f34
2478         $MCREATE $DIR/f34 || error
2479         $GETSTRIPE $DIR/f34 2>&1 | grep -q "no stripe info" || error
2480         $TRUNCATE $DIR/f34 $TEST_34_SIZE || error
2481         $GETSTRIPE $DIR/f34 2>&1 | grep -q "no stripe info" || error
2482         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 || error
2483 }
2484 run_test 34a "truncate file that has not been opened ==========="
2485
2486 test_34b() {
2487         [ ! -f $DIR/f34 ] && test_34a
2488         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 || error
2489         $OPENFILE -f O_RDONLY $DIR/f34
2490         $GETSTRIPE $DIR/f34 2>&1 | grep -q "no stripe info" || error
2491         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 || error
2492 }
2493 run_test 34b "O_RDONLY opening file doesn't create objects ====="
2494
2495 test_34c() {
2496         [ ! -f $DIR/f34 ] && test_34a
2497         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 || error
2498         $OPENFILE -f O_RDWR $DIR/f34
2499         $GETSTRIPE $DIR/f34 2>&1 | grep -q "no stripe info" && error
2500         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 || error
2501 }
2502 run_test 34c "O_RDWR opening file-with-size works =============="
2503
2504 test_34d() {
2505         [ ! -f $DIR/f34 ] && test_34a
2506         dd if=/dev/zero of=$DIR/f34 conv=notrunc bs=4k count=1 || error
2507         $CHECKSTAT -s $TEST_34_SIZE $DIR/f34 || error
2508         rm $DIR/f34
2509 }
2510 run_test 34d "write to sparse file ============================="
2511
2512 test_34e() {
2513         rm -f $DIR/f34e
2514         $MCREATE $DIR/f34e || error
2515         $TRUNCATE $DIR/f34e 1000 || error
2516         $CHECKSTAT -s 1000 $DIR/f34e || error
2517         $OPENFILE -f O_RDWR $DIR/f34e
2518         $CHECKSTAT -s 1000 $DIR/f34e || error
2519 }
2520 run_test 34e "create objects, some with size and some without =="
2521
2522 test_34f() { # bug 6242, 6243
2523         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2524         SIZE34F=48000
2525         rm -f $DIR/f34f
2526         $MCREATE $DIR/f34f || error
2527         $TRUNCATE $DIR/f34f $SIZE34F || error "truncating $DIR/f3f to $SIZE34F"
2528         dd if=$DIR/f34f of=$TMP/f34f
2529         $CHECKSTAT -s $SIZE34F $TMP/f34f || error "$TMP/f34f not $SIZE34F bytes"
2530         dd if=/dev/zero of=$TMP/f34fzero bs=$SIZE34F count=1
2531         cmp $DIR/f34f $TMP/f34fzero || error "$DIR/f34f not all zero"
2532         cmp $TMP/f34f $TMP/f34fzero || error "$TMP/f34f not all zero"
2533         rm $TMP/f34f $TMP/f34fzero $DIR/f34f
2534 }
2535 run_test 34f "read from a file with no objects until EOF ======="
2536
2537 test_34g() {
2538         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2539         dd if=/dev/zero of=$DIR/$tfile bs=1 count=100 seek=$TEST_34_SIZE || error
2540         $TRUNCATE $DIR/$tfile $((TEST_34_SIZE / 2))|| error
2541         $CHECKSTAT -s $((TEST_34_SIZE / 2)) $DIR/$tfile || error "truncate failed"
2542         cancel_lru_locks osc
2543         $CHECKSTAT -s $((TEST_34_SIZE / 2)) $DIR/$tfile || \
2544                 error "wrong size after lock cancel"
2545
2546         $TRUNCATE $DIR/$tfile $TEST_34_SIZE || error
2547         $CHECKSTAT -s $TEST_34_SIZE $DIR/$tfile || \
2548                 error "expanding truncate failed"
2549         cancel_lru_locks osc
2550         $CHECKSTAT -s $TEST_34_SIZE $DIR/$tfile || \
2551                 error "wrong expanded size after lock cancel"
2552 }
2553 run_test 34g "truncate long file ==============================="
2554
2555 test_34h() {
2556         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2557         local gid=10
2558         local sz=1000
2559
2560         dd if=/dev/zero of=$DIR/$tfile bs=1M count=10 || error
2561         sync # Flush the cache so that multiop below does not block on cache
2562              # flush when getting the group lock
2563         $MULTIOP $DIR/$tfile OG${gid}T${sz}g${gid}c &
2564         MULTIPID=$!
2565         sleep 2
2566
2567         if [[ `ps h -o comm -p $MULTIPID` == "multiop" ]]; then
2568                 error "Multiop blocked on ftruncate, pid=$MULTIPID"
2569                 kill -9 $MULTIPID
2570         fi
2571         wait $MULTIPID
2572         local nsz=`stat -c %s $DIR/$tfile`
2573         [[ $nsz == $sz ]] || error "New size wrong $nsz != $sz"
2574 }
2575 run_test 34h "ftruncate file under grouplock should not block"
2576
2577 test_35a() {
2578         cp /bin/sh $DIR/f35a
2579         chmod 444 $DIR/f35a
2580         chown $RUNAS_ID $DIR/f35a
2581         $RUNAS $DIR/f35a && error || true
2582         rm $DIR/f35a
2583 }
2584 run_test 35a "exec file with mode 444 (should return and not leak) ====="
2585
2586 test_36a() {
2587         rm -f $DIR/f36
2588         utime $DIR/f36 || error
2589 }
2590 run_test 36a "MDS utime check (mknod, utime) ==================="
2591
2592 test_36b() {
2593         echo "" > $DIR/f36
2594         utime $DIR/f36 || error
2595 }
2596 run_test 36b "OST utime check (open, utime) ===================="
2597
2598 test_36c() {
2599         rm -f $DIR/d36/f36
2600         test_mkdir $DIR/d36
2601         chown $RUNAS_ID $DIR/d36
2602         $RUNAS utime $DIR/d36/f36 || error
2603 }
2604 run_test 36c "non-root MDS utime check (mknod, utime) =========="
2605
2606 test_36d() {
2607         [ ! -d $DIR/d36 ] && test_36c
2608         echo "" > $DIR/d36/f36
2609         $RUNAS utime $DIR/d36/f36 || error
2610 }
2611 run_test 36d "non-root OST utime check (open, utime) ==========="
2612
2613 test_36e() {
2614         [ $RUNAS_ID -eq $UID ] && skip_env "RUNAS_ID = UID = $UID -- skipping" && return
2615         test_mkdir -p $DIR/$tdir
2616         touch $DIR/$tdir/$tfile
2617         $RUNAS utime $DIR/$tdir/$tfile && \
2618                 error "utime worked, expected failure" || true
2619 }
2620 run_test 36e "utime on non-owned file (should return error) ===="
2621
2622 subr_36fh() {
2623         local fl="$1"
2624         local LANG_SAVE=$LANG
2625         local LC_LANG_SAVE=$LC_LANG
2626         export LANG=C LC_LANG=C # for date language
2627
2628         DATESTR="Dec 20  2000"
2629         test_mkdir -p $DIR/$tdir
2630         lctl set_param fail_loc=$fl
2631         date; date +%s
2632         cp /etc/hosts $DIR/$tdir/$tfile
2633         sync & # write RPC generated with "current" inode timestamp, but delayed
2634         sleep 1
2635         touch --date="$DATESTR" $DIR/$tdir/$tfile # setattr timestamp in past
2636         LS_BEFORE="`ls -l $DIR/$tdir/$tfile`" # old timestamp from client cache
2637         cancel_lru_locks osc
2638         LS_AFTER="`ls -l $DIR/$tdir/$tfile`"  # timestamp from OST object
2639         date; date +%s
2640         [ "$LS_BEFORE" != "$LS_AFTER" ] && \
2641                 echo "BEFORE: $LS_BEFORE" && \
2642                 echo "AFTER : $LS_AFTER" && \
2643                 echo "WANT  : $DATESTR" && \
2644                 error "$DIR/$tdir/$tfile timestamps changed" || true
2645
2646         export LANG=$LANG_SAVE LC_LANG=$LC_LANG_SAVE
2647 }
2648
2649 test_36f() {
2650         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2651         #define OBD_FAIL_OST_BRW_PAUSE_BULK 0x214
2652         subr_36fh "0x80000214"
2653 }
2654 run_test 36f "utime on file racing with OST BRW write =========="
2655
2656 test_36g() {
2657         remote_ost_nodsh && skip "remote OST with nodsh" && return
2658         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2659         local fmd_max_age
2660         local fmd_before
2661         local fmd_after
2662
2663         test_mkdir -p $DIR/$tdir
2664         fmd_max_age=$(do_facet ost1 \
2665                 "lctl get_param -n obdfilter.*.client_cache_seconds 2> /dev/null | \
2666                 head -n 1")
2667
2668         fmd_before=$(do_facet ost1 \
2669                 "awk '/ll_fmd_cache/ {print \\\$2}' /proc/slabinfo")
2670         touch $DIR/$tdir/$tfile
2671         sleep $((fmd_max_age + 12))
2672         fmd_after=$(do_facet ost1 \
2673                 "awk '/ll_fmd_cache/ {print \\\$2}' /proc/slabinfo")
2674
2675         echo "fmd_before: $fmd_before"
2676         echo "fmd_after: $fmd_after"
2677         [ "$fmd_after" -gt "$fmd_before" ] && \
2678                 echo "AFTER: $fmd_after > BEFORE: $fmd_before" && \
2679                 error "fmd didn't expire after ping" || true
2680 }
2681 run_test 36g "filter mod data cache expiry ====================="
2682
2683 test_36h() {
2684         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2685         #define OBD_FAIL_OST_BRW_PAUSE_BULK2 0x227
2686         subr_36fh "0x80000227"
2687 }
2688 run_test 36h "utime on file racing with OST BRW write =========="
2689
2690 # test_37 - duplicate with tests 32q 32r
2691
2692 test_38() {
2693         local file=$DIR/$tfile
2694         touch $file
2695         openfile -f O_DIRECTORY $file
2696         local RC=$?
2697         local ENOTDIR=20
2698         [ $RC -eq 0 ] && error "opened file $file with O_DIRECTORY" || true
2699         [ $RC -eq $ENOTDIR ] || error "error $RC should be ENOTDIR ($ENOTDIR)"
2700 }
2701 run_test 38 "open a regular file with O_DIRECTORY should return -ENOTDIR ==="
2702
2703 test_39() {
2704         touch $DIR/$tfile
2705         touch $DIR/${tfile}2
2706 #       ls -l  $DIR/$tfile $DIR/${tfile}2
2707 #       ls -lu  $DIR/$tfile $DIR/${tfile}2
2708 #       ls -lc  $DIR/$tfile $DIR/${tfile}2
2709         sleep 2
2710         $OPENFILE -f O_CREAT:O_TRUNC:O_WRONLY $DIR/${tfile}2
2711         if [ ! $DIR/${tfile}2 -nt $DIR/$tfile ]; then
2712                 echo "mtime"
2713                 ls -l --full-time $DIR/$tfile $DIR/${tfile}2
2714                 echo "atime"
2715                 ls -lu --full-time $DIR/$tfile $DIR/${tfile}2
2716                 echo "ctime"
2717                 ls -lc --full-time $DIR/$tfile $DIR/${tfile}2
2718                 error "O_TRUNC didn't change timestamps"
2719         fi
2720 }
2721 run_test 39 "mtime changed on create ==========================="
2722
2723 test_39b() {
2724         test_mkdir -p $DIR/$tdir
2725         cp -p /etc/passwd $DIR/$tdir/fopen
2726         cp -p /etc/passwd $DIR/$tdir/flink
2727         cp -p /etc/passwd $DIR/$tdir/funlink
2728         cp -p /etc/passwd $DIR/$tdir/frename
2729         ln $DIR/$tdir/funlink $DIR/$tdir/funlink2
2730
2731         sleep 1
2732         echo "aaaaaa" >> $DIR/$tdir/fopen
2733         echo "aaaaaa" >> $DIR/$tdir/flink
2734         echo "aaaaaa" >> $DIR/$tdir/funlink
2735         echo "aaaaaa" >> $DIR/$tdir/frename
2736
2737         local open_new=`stat -c %Y $DIR/$tdir/fopen`
2738         local link_new=`stat -c %Y $DIR/$tdir/flink`
2739         local unlink_new=`stat -c %Y $DIR/$tdir/funlink`
2740         local rename_new=`stat -c %Y $DIR/$tdir/frename`
2741
2742         cat $DIR/$tdir/fopen > /dev/null
2743         ln $DIR/$tdir/flink $DIR/$tdir/flink2
2744         rm -f $DIR/$tdir/funlink2
2745         mv -f $DIR/$tdir/frename $DIR/$tdir/frename2
2746
2747         for (( i=0; i < 2; i++ )) ; do
2748                 local open_new2=`stat -c %Y $DIR/$tdir/fopen`
2749                 local link_new2=`stat -c %Y $DIR/$tdir/flink`
2750                 local unlink_new2=`stat -c %Y $DIR/$tdir/funlink`
2751                 local rename_new2=`stat -c %Y $DIR/$tdir/frename2`
2752
2753                 [ $open_new2 -eq $open_new ] || error "open file reverses mtime"
2754                 [ $link_new2 -eq $link_new ] || error "link file reverses mtime"
2755                 [ $unlink_new2 -eq $unlink_new ] || error "unlink file reverses mtime"
2756                 [ $rename_new2 -eq $rename_new ] || error "rename file reverses mtime"
2757
2758                 cancel_lru_locks osc
2759                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
2760         done
2761 }
2762 run_test 39b "mtime change on open, link, unlink, rename  ======"
2763
2764 # this should be set to past
2765 TEST_39_MTIME=`date -d "1 year ago" +%s`
2766
2767 # bug 11063
2768 test_39c() {
2769         touch $DIR1/$tfile
2770         sleep 2
2771         local mtime0=`stat -c %Y $DIR1/$tfile`
2772
2773         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
2774         local mtime1=`stat -c %Y $DIR1/$tfile`
2775         [ "$mtime1" = $TEST_39_MTIME ] || \
2776                 error "mtime is not set to past: $mtime1, should be $TEST_39_MTIME"
2777
2778         local d1=`date +%s`
2779         echo hello >> $DIR1/$tfile
2780         local d2=`date +%s`
2781         local mtime2=`stat -c %Y $DIR1/$tfile`
2782         [ "$mtime2" -ge "$d1" ] && [ "$mtime2" -le "$d2" ] || \
2783                 error "mtime is not updated on write: $d1 <= $mtime2 <= $d2"
2784
2785         mv $DIR1/$tfile $DIR1/$tfile-1
2786
2787         for (( i=0; i < 2; i++ )) ; do
2788                 local mtime3=`stat -c %Y $DIR1/$tfile-1`
2789                 [ "$mtime2" = "$mtime3" ] || \
2790                         error "mtime ($mtime2) changed (to $mtime3) on rename"
2791
2792                 cancel_lru_locks osc
2793                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
2794         done
2795 }
2796 run_test 39c "mtime change on rename ==========================="
2797
2798 # bug 21114
2799 test_39d() {
2800         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2801         touch $DIR1/$tfile
2802
2803         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
2804
2805         for (( i=0; i < 2; i++ )) ; do
2806                 local mtime=`stat -c %Y $DIR1/$tfile`
2807                 [ $mtime = $TEST_39_MTIME ] || \
2808                         error "mtime($mtime) is not set to $TEST_39_MTIME"
2809
2810                 cancel_lru_locks osc
2811                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
2812         done
2813 }
2814 run_test 39d "create, utime, stat =============================="
2815
2816 # bug 21114
2817 test_39e() {
2818         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2819         touch $DIR1/$tfile
2820         local mtime1=`stat -c %Y $DIR1/$tfile`
2821
2822         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
2823
2824         for (( i=0; i < 2; i++ )) ; do
2825                 local mtime2=`stat -c %Y $DIR1/$tfile`
2826                 [ $mtime2 = $TEST_39_MTIME ] || \
2827                         error "mtime($mtime2) is not set to $TEST_39_MTIME"
2828
2829                 cancel_lru_locks osc
2830                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
2831         done
2832 }
2833 run_test 39e "create, stat, utime, stat ========================"
2834
2835 # bug 21114
2836 test_39f() {
2837         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2838         touch $DIR1/$tfile
2839         mtime1=`stat -c %Y $DIR1/$tfile`
2840
2841         sleep 2
2842         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
2843
2844         for (( i=0; i < 2; i++ )) ; do
2845                 local mtime2=`stat -c %Y $DIR1/$tfile`
2846                 [ $mtime2 = $TEST_39_MTIME ] || \
2847                         error "mtime($mtime2) is not set to $TEST_39_MTIME"
2848
2849                 cancel_lru_locks osc
2850                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
2851         done
2852 }
2853 run_test 39f "create, stat, sleep, utime, stat ================="
2854
2855 # bug 11063
2856 test_39g() {
2857         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2858         echo hello >> $DIR1/$tfile
2859         local mtime1=`stat -c %Y $DIR1/$tfile`
2860
2861         sleep 2
2862         chmod o+r $DIR1/$tfile
2863
2864         for (( i=0; i < 2; i++ )) ; do
2865                 local mtime2=`stat -c %Y $DIR1/$tfile`
2866                 [ "$mtime1" = "$mtime2" ] || \
2867                         error "lost mtime: $mtime2, should be $mtime1"
2868
2869                 cancel_lru_locks osc
2870                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
2871         done
2872 }
2873 run_test 39g "write, chmod, stat ==============================="
2874
2875 # bug 11063
2876 test_39h() {
2877         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2878         touch $DIR1/$tfile
2879         sleep 1
2880
2881         local d1=`date`
2882         echo hello >> $DIR1/$tfile
2883         local mtime1=`stat -c %Y $DIR1/$tfile`
2884
2885         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
2886         local d2=`date`
2887         if [ "$d1" != "$d2" ]; then
2888                 echo "write and touch not within one second"
2889         else
2890                 for (( i=0; i < 2; i++ )) ; do
2891                         local mtime2=`stat -c %Y $DIR1/$tfile`
2892                         [ "$mtime2" = $TEST_39_MTIME ] || \
2893                                 error "lost mtime: $mtime2, should be $TEST_39_MTIME"
2894
2895                         cancel_lru_locks osc
2896                         if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
2897                 done
2898         fi
2899 }
2900 run_test 39h "write, utime within one second, stat ============="
2901
2902 test_39i() {
2903         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2904         touch $DIR1/$tfile
2905         sleep 1
2906
2907         echo hello >> $DIR1/$tfile
2908         local mtime1=`stat -c %Y $DIR1/$tfile`
2909
2910         mv $DIR1/$tfile $DIR1/$tfile-1
2911
2912         for (( i=0; i < 2; i++ )) ; do
2913                 local mtime2=`stat -c %Y $DIR1/$tfile-1`
2914
2915                 [ "$mtime1" = "$mtime2" ] || \
2916                         error "lost mtime: $mtime2, should be $mtime1"
2917
2918                 cancel_lru_locks osc
2919                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
2920         done
2921 }
2922 run_test 39i "write, rename, stat =============================="
2923
2924 test_39j() {
2925         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2926         start_full_debug_logging
2927         touch $DIR1/$tfile
2928         sleep 1
2929
2930         #define OBD_FAIL_OSC_DELAY_SETTIME       0x412
2931         lctl set_param fail_loc=0x80000412
2932         multiop_bg_pause $DIR1/$tfile oO_RDWR:w2097152_c ||
2933                 error "multiop failed"
2934         local multipid=$!
2935         local mtime1=`stat -c %Y $DIR1/$tfile`
2936
2937         mv $DIR1/$tfile $DIR1/$tfile-1
2938
2939         kill -USR1 $multipid
2940         wait $multipid || error "multiop close failed"
2941
2942         for (( i=0; i < 2; i++ )) ; do
2943                 local mtime2=`stat -c %Y $DIR1/$tfile-1`
2944                 [ "$mtime1" = "$mtime2" ] ||
2945                         error "mtime is lost on close: $mtime2, " \
2946                               "should be $mtime1"
2947
2948                 cancel_lru_locks osc
2949                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
2950         done
2951         lctl set_param fail_loc=0
2952         stop_full_debug_logging
2953 }
2954 run_test 39j "write, rename, close, stat ======================="
2955
2956 test_39k() {
2957         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2958         touch $DIR1/$tfile
2959         sleep 1
2960
2961         multiop_bg_pause $DIR1/$tfile oO_RDWR:w2097152_c || error "multiop failed"
2962         local multipid=$!
2963         local mtime1=`stat -c %Y $DIR1/$tfile`
2964
2965         touch -m -d @$TEST_39_MTIME $DIR1/$tfile
2966
2967         kill -USR1 $multipid
2968         wait $multipid || error "multiop close failed"
2969
2970         for (( i=0; i < 2; i++ )) ; do
2971                 local mtime2=`stat -c %Y $DIR1/$tfile`
2972
2973                 [ "$mtime2" = $TEST_39_MTIME ] || \
2974                         error "mtime is lost on close: $mtime2, should be $TEST_39_MTIME"
2975
2976                 cancel_lru_locks osc
2977                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
2978         done
2979 }
2980 run_test 39k "write, utime, close, stat ========================"
2981
2982 # this should be set to future
2983 TEST_39_ATIME=`date -d "1 year" +%s`
2984
2985 test_39l() {
2986         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
2987         remote_mds_nodsh && skip "remote MDS with nodsh" && return
2988         local atime_diff=$(do_facet $SINGLEMDS \
2989                                 lctl get_param -n mdd.*MDT0000*.atime_diff)
2990         rm -rf $DIR/$tdir
2991         mkdir -p $DIR/$tdir
2992
2993         # test setting directory atime to future
2994         touch -a -d @$TEST_39_ATIME $DIR/$tdir
2995         local atime=$(stat -c %X $DIR/$tdir)
2996         [ "$atime" = $TEST_39_ATIME ] || \
2997                 error "atime is not set to future: $atime, $TEST_39_ATIME"
2998
2999         # test setting directory atime from future to now
3000         local d1=$(date +%s)
3001         ls $DIR/$tdir
3002         local d2=$(date +%s)
3003
3004         cancel_lru_locks mdc
3005         atime=$(stat -c %X $DIR/$tdir)
3006         [ "$atime" -ge "$d1" -a "$atime" -le "$d2" ] || \
3007                 error "atime is not updated from future: $atime, $d1<atime<$d2"
3008
3009         do_facet $SINGLEMDS lctl set_param -n mdd.*MDT0000*.atime_diff=2
3010         sleep 3
3011
3012         # test setting directory atime when now > dir atime + atime_diff
3013         d1=$(date +%s)
3014         ls $DIR/$tdir
3015         d2=$(date +%s)
3016         cancel_lru_locks mdc
3017         atime=$(stat -c %X $DIR/$tdir)
3018         [ "$atime" -ge "$d1" -a "$atime" -le "$d2" ] || \
3019                 error "atime is not updated  : $atime, should be $d2"
3020
3021         do_facet $SINGLEMDS lctl set_param -n mdd.*MDT0000*.atime_diff=60
3022         sleep 3
3023
3024         # test not setting directory atime when now < dir atime + atime_diff
3025         ls $DIR/$tdir
3026         cancel_lru_locks mdc
3027         atime=$(stat -c %X $DIR/$tdir)
3028         [ "$atime" -ge "$d1" -a "$atime" -le "$d2" ] || \
3029                 error "atime is updated to $atime, should remain $d1<atime<$d2"
3030
3031         do_facet $SINGLEMDS \
3032                 lctl set_param -n mdd.*MDT0000*.atime_diff=$atime_diff
3033 }
3034 run_test 39l "directory atime update ==========================="
3035
3036 test_39m() {
3037         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
3038         touch $DIR1/$tfile
3039         sleep 2
3040         local far_past_mtime=$(date -d "May 29 1953" +%s)
3041         local far_past_atime=$(date -d "Dec 17 1903" +%s)
3042
3043         touch -m -d @$far_past_mtime $DIR1/$tfile
3044         touch -a -d @$far_past_atime $DIR1/$tfile
3045
3046         for (( i=0; i < 2; i++ )) ; do
3047                 local timestamps=$(stat -c "%X %Y" $DIR1/$tfile)
3048                 [ "$timestamps" = "$far_past_atime $far_past_mtime" ] || \
3049                         error "atime or mtime set incorrectly"
3050
3051                 cancel_lru_locks osc
3052                 if [ $i = 0 ] ; then echo "repeat after cancel_lru_locks"; fi
3053         done
3054 }
3055 run_test 39m "test atime and mtime before 1970"
3056
3057 test_40() {
3058         dd if=/dev/zero of=$DIR/f40 bs=4096 count=1
3059         $RUNAS $OPENFILE -f O_WRONLY:O_TRUNC $DIR/f40 && error
3060         $CHECKSTAT -t file -s 4096 $DIR/f40 || error
3061 }
3062 run_test 40 "failed open(O_TRUNC) doesn't truncate ============="
3063
3064 test_41() {
3065         # bug 1553
3066         small_write $DIR/f41 18
3067 }
3068 run_test 41 "test small file write + fstat ====================="
3069
3070 count_ost_writes() {
3071         lctl get_param -n osc.*.stats |
3072             awk -vwrites=0 '/ost_write/ { writes += $2 } END { print writes; }'
3073 }
3074
3075 # decent default
3076 WRITEBACK_SAVE=500
3077 DIRTY_RATIO_SAVE=40
3078 MAX_DIRTY_RATIO=50
3079 BG_DIRTY_RATIO_SAVE=10
3080 MAX_BG_DIRTY_RATIO=25
3081
3082 start_writeback() {
3083         trap 0
3084         # in 2.6, restore /proc/sys/vm/dirty_writeback_centisecs,
3085         # dirty_ratio, dirty_background_ratio
3086         if [ -f /proc/sys/vm/dirty_writeback_centisecs ]; then
3087                 sysctl -w vm.dirty_writeback_centisecs=$WRITEBACK_SAVE
3088                 sysctl -w vm.dirty_background_ratio=$BG_DIRTY_RATIO_SAVE
3089                 sysctl -w vm.dirty_ratio=$DIRTY_RATIO_SAVE
3090         else
3091                 # if file not here, we are a 2.4 kernel
3092                 kill -CONT `pidof kupdated`
3093         fi
3094 }
3095
3096 stop_writeback() {
3097         # setup the trap first, so someone cannot exit the test at the
3098         # exact wrong time and mess up a machine
3099         trap start_writeback EXIT
3100         # in 2.6, save and 0 /proc/sys/vm/dirty_writeback_centisecs
3101         if [ -f /proc/sys/vm/dirty_writeback_centisecs ]; then
3102                 WRITEBACK_SAVE=`sysctl -n vm.dirty_writeback_centisecs`
3103                 sysctl -w vm.dirty_writeback_centisecs=0
3104                 sysctl -w vm.dirty_writeback_centisecs=0
3105                 # save and increase /proc/sys/vm/dirty_ratio
3106                 DIRTY_RATIO_SAVE=`sysctl -n vm.dirty_ratio`
3107                 sysctl -w vm.dirty_ratio=$MAX_DIRTY_RATIO
3108                 # save and increase /proc/sys/vm/dirty_background_ratio
3109                 BG_DIRTY_RATIO_SAVE=`sysctl -n vm.dirty_background_ratio`
3110                 sysctl -w vm.dirty_background_ratio=$MAX_BG_DIRTY_RATIO
3111         else
3112                 # if file not here, we are a 2.4 kernel
3113                 kill -STOP `pidof kupdated`
3114         fi
3115 }
3116
3117 # ensure that all stripes have some grant before we test client-side cache
3118 setup_test42() {
3119         for i in `seq -f $DIR/f42-%g 1 $OSTCOUNT`; do
3120                 dd if=/dev/zero of=$i bs=4k count=1
3121                 rm $i
3122         done
3123 }
3124
3125 # Tests 42* verify that our behaviour is correct WRT caching, file closure,
3126 # file truncation, and file removal.
3127 test_42a() {
3128         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
3129         setup_test42
3130         cancel_lru_locks osc
3131         stop_writeback
3132         sync; sleep 1; sync # just to be safe
3133         BEFOREWRITES=`count_ost_writes`
3134         lctl get_param -n osc.*[oO][sS][cC][_-]*.cur_grant_bytes | grep "[0-9]"
3135         dd if=/dev/zero of=$DIR/f42a bs=1024 count=100
3136         AFTERWRITES=`count_ost_writes`
3137         [ $BEFOREWRITES -eq $AFTERWRITES ] || \
3138                 error "$BEFOREWRITES < $AFTERWRITES"
3139         start_writeback
3140 }
3141 run_test 42a "ensure that we don't flush on close =============="
3142
3143 test_42b() {
3144         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
3145         setup_test42
3146         cancel_lru_locks osc
3147         stop_writeback
3148         sync
3149         dd if=/dev/zero of=$DIR/f42b bs=1024 count=100
3150         BEFOREWRITES=`count_ost_writes`
3151         $MUNLINK $DIR/f42b || error "$MUNLINK $DIR/f42b: $?"
3152         AFTERWRITES=`count_ost_writes`
3153         if [ $BEFOREWRITES -lt $AFTERWRITES ]; then
3154                 error "$BEFOREWRITES < $AFTERWRITES on unlink"
3155         fi
3156         BEFOREWRITES=`count_ost_writes`
3157         sync || error "sync: $?"
3158         AFTERWRITES=`count_ost_writes`
3159         if [ $BEFOREWRITES -lt $AFTERWRITES ]; then
3160                 error "$BEFOREWRITES < $AFTERWRITES on sync"
3161         fi
3162         dmesg | grep 'error from obd_brw_async' && error 'error writing back'
3163         start_writeback
3164         return 0
3165 }
3166 run_test 42b "test destroy of file with cached dirty data ======"
3167
3168 # if these tests just want to test the effect of truncation,
3169 # they have to be very careful.  consider:
3170 # - the first open gets a {0,EOF}PR lock
3171 # - the first write conflicts and gets a {0, count-1}PW
3172 # - the rest of the writes are under {count,EOF}PW
3173 # - the open for truncate tries to match a {0,EOF}PR
3174 #   for the filesize and cancels the PWs.
3175 # any number of fixes (don't get {0,EOF} on open, match
3176 # composite locks, do smarter file size management) fix
3177 # this, but for now we want these tests to verify that
3178 # the cancellation with truncate intent works, so we
3179 # start the file with a full-file pw lock to match against
3180 # until the truncate.
3181 trunc_test() {
3182         test=$1
3183         file=$DIR/$test
3184         offset=$2
3185         cancel_lru_locks osc
3186         stop_writeback
3187         # prime the file with 0,EOF PW to match
3188         touch $file
3189         $TRUNCATE $file 0
3190         sync; sync
3191         # now the real test..
3192         dd if=/dev/zero of=$file bs=1024 count=100
3193         BEFOREWRITES=`count_ost_writes`
3194         $TRUNCATE $file $offset
3195         cancel_lru_locks osc
3196         AFTERWRITES=`count_ost_writes`
3197         start_writeback
3198 }
3199
3200 test_42c() {
3201         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
3202         trunc_test 42c 1024
3203         [ $BEFOREWRITES -eq $AFTERWRITES ] && \
3204             error "beforewrites $BEFOREWRITES == afterwrites $AFTERWRITES on truncate"
3205         rm $file
3206 }
3207 run_test 42c "test partial truncate of file with cached dirty data"
3208
3209 test_42d() {
3210         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
3211         trunc_test 42d 0
3212         [ $BEFOREWRITES -eq $AFTERWRITES ] || \
3213             error "beforewrites $BEFOREWRITES != afterwrites $AFTERWRITES on truncate"
3214         rm $file
3215 }
3216 run_test 42d "test complete truncate of file with cached dirty data"
3217
3218 test_42e() { # bug22074
3219         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
3220         local TDIR=$DIR/${tdir}e
3221         local pagesz=$(page_size)
3222         local pages=16 # hardcoded 16 pages, don't change it.
3223         local files=$((OSTCOUNT * 500)) # hopefully 500 files on each OST
3224         local proc_osc0="osc.${FSNAME}-OST0000-osc-[^MDT]*"
3225         local max_dirty_mb
3226         local warmup_files
3227
3228         test_mkdir -p $DIR/${tdir}e
3229         $SETSTRIPE -c 1 $TDIR
3230         createmany -o $TDIR/f $files
3231
3232         max_dirty_mb=$($LCTL get_param -n $proc_osc0/max_dirty_mb)
3233
3234         # we assume that with $OSTCOUNT files, at least one of them will
3235         # be allocated on OST0.
3236         warmup_files=$((OSTCOUNT * max_dirty_mb))
3237         createmany -o $TDIR/w $warmup_files
3238
3239         # write a large amount of data into one file and sync, to get good
3240         # avail_grant number from OST.
3241         for ((i=0; i<$warmup_files; i++)); do
3242                 idx=$($GETSTRIPE -i $TDIR/w$i)
3243                 [ $idx -ne 0 ] && continue
3244                 dd if=/dev/zero of=$TDIR/w$i bs="$max_dirty_mb"M count=1
3245                 break
3246         done
3247         [ $i -gt $warmup_files ] && error "OST0 is still cold"
3248         sync
3249         $LCTL get_param $proc_osc0/cur_dirty_bytes
3250         $LCTL get_param $proc_osc0/cur_grant_bytes
3251
3252         # create as much dirty pages as we can while not to trigger the actual
3253         # RPCs directly. but depends on the env, VFS may trigger flush during this
3254         # period, hopefully we are good.
3255         for ((i=0; i<$warmup_files; i++)); do
3256                 idx=$($GETSTRIPE -i $TDIR/w$i)
3257                 [ $idx -ne 0 ] && continue
3258                 dd if=/dev/zero of=$TDIR/w$i bs=1M count=1 2>/dev/null
3259         done
3260         $LCTL get_param $proc_osc0/cur_dirty_bytes
3261         $LCTL get_param $proc_osc0/cur_grant_bytes
3262
3263         # perform the real test
3264         $LCTL set_param $proc_osc0/rpc_stats 0
3265         for ((;i<$files; i++)); do
3266                 [ $($GETSTRIPE -i $TDIR/f$i) -eq 0 ] || continue
3267                 dd if=/dev/zero of=$TDIR/f$i bs=$pagesz count=$pages 2>/dev/null
3268         done
3269         sync
3270         $LCTL get_param $proc_osc0/rpc_stats
3271
3272         local percent=0
3273         local have_ppr=false
3274         $LCTL get_param $proc_osc0/rpc_stats |
3275                 while read PPR RRPC RPCT RCUM BAR WRPC WPCT WCUM; do
3276                         # skip lines until we are at the RPC histogram data
3277                         [ "$PPR" == "pages" ] && have_ppr=true && continue
3278                         $have_ppr || continue
3279
3280                         # we only want the percent stat for < 16 pages
3281                         [ $(echo $PPR | tr -d ':') -ge $pages ] && break
3282
3283                         percent=$((percent + WPCT))
3284                         if [ $percent -gt 15 ]; then
3285                                 error "less than 16-pages write RPCs" \
3286                                       "$percent% > 15%"
3287                                 break
3288                         fi
3289                 done
3290         rm -rf $TDIR
3291 }
3292 run_test 42e "verify sub-RPC writes are not done synchronously"
3293
3294 test_43() {
3295         test_mkdir -p $DIR/$tdir
3296         cp -p /bin/ls $DIR/$tdir/$tfile
3297         $MULTIOP $DIR/$tdir/$tfile Ow_c &
3298         pid=$!
3299         # give multiop a chance to open
3300         sleep 1
3301
3302         $DIR/$tdir/$tfile && error || true
3303         kill -USR1 $pid
3304 }
3305 run_test 43 "execution of file opened for write should return -ETXTBSY"
3306
3307 test_43a() {
3308         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
3309         test_mkdir -p $DIR/$tdir
3310         cp -p `which $MULTIOP` $DIR/$tdir/multiop ||
3311                         cp -p multiop $DIR/$tdir/multiop
3312         MULTIOP_PROG=$DIR/$tdir/multiop multiop_bg_pause $TMP/test43.junk O_c ||
3313                         return 1
3314         MULTIOP_PID=$!
3315         $MULTIOP $DIR/$tdir/multiop Oc && error "expected error, got success"
3316         kill -USR1 $MULTIOP_PID || return 2
3317         wait $MULTIOP_PID || return 3
3318         rm $TMP/test43.junk
3319 }
3320 run_test 43a "open(RDWR) of file being executed should return -ETXTBSY"
3321
3322 test_43b() {
3323         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
3324         test_mkdir -p $DIR/$tdir
3325         cp -p `which $MULTIOP` $DIR/$tdir/multiop ||
3326                         cp -p multiop $DIR/$tdir/multiop
3327         MULTIOP_PROG=$DIR/$tdir/multiop multiop_bg_pause $TMP/test43.junk O_c ||
3328                         return 1
3329         MULTIOP_PID=$!
3330         $TRUNCATE $DIR/$tdir/multiop 0 && error "expected error, got success"
3331         kill -USR1 $MULTIOP_PID || return 2
3332         wait $MULTIOP_PID || return 3
3333         rm $TMP/test43.junk
3334 }
3335 run_test 43b "truncate of file being executed should return -ETXTBSY"
3336
3337 test_43c() {
3338         local testdir="$DIR/$tdir"
3339         test_mkdir -p $DIR/$tdir
3340         cp $SHELL $testdir/
3341         ( cd $(dirname $SHELL) && md5sum $(basename $SHELL) ) | \
3342                 ( cd $testdir && md5sum -c)
3343 }
3344 run_test 43c "md5sum of copy into lustre========================"
3345
3346 test_44() {
3347         [  "$OSTCOUNT" -lt "2" ] && skip_env "skipping 2-stripe test" && return
3348         dd if=/dev/zero of=$DIR/f1 bs=4k count=1 seek=1023
3349         dd if=$DIR/f1 bs=4k count=1 > /dev/null
3350 }
3351 run_test 44 "zero length read from a sparse stripe ============="
3352
3353 test_44a() {
3354     local nstripe=`$LCTL lov_getconfig $DIR | grep default_stripe_count: | \
3355                          awk '{print $2}'`
3356     [ -z "$nstripe" ] && skip "can't get stripe info" && return
3357     [ "$nstripe" -gt "$OSTCOUNT" ] && skip "Wrong default_stripe_count: $nstripe (OSTCOUNT: $OSTCOUNT)" && return
3358     local stride=`$LCTL lov_getconfig $DIR | grep default_stripe_size: | \
3359                       awk '{print $2}'`
3360     if [ $nstripe -eq 0 -o $nstripe -eq -1 ] ; then
3361         nstripe=`$LCTL lov_getconfig $DIR | grep obd_count: | awk '{print $2}'`
3362     fi
3363
3364     OFFSETS="0 $((stride/2)) $((stride-1))"
3365     for offset in $OFFSETS ; do
3366       for i in `seq 0 $((nstripe-1))`; do
3367         local GLOBALOFFSETS=""
3368         local size=$((((i + 2 * $nstripe )*$stride + $offset)))  # Bytes
3369         local myfn=$DIR/d44a-$size
3370         echo "--------writing $myfn at $size"
3371         ll_sparseness_write $myfn $size  || error "ll_sparseness_write"
3372         GLOBALOFFSETS="$GLOBALOFFSETS $size"
3373         ll_sparseness_verify $myfn $GLOBALOFFSETS \
3374                             || error "ll_sparseness_verify $GLOBALOFFSETS"
3375
3376         for j in `seq 0 $((nstripe-1))`; do
3377             size=$((((j + $nstripe )*$stride + $offset)))  # Bytes
3378             ll_sparseness_write $myfn $size || error "ll_sparseness_write"
3379             GLOBALOFFSETS="$GLOBALOFFSETS $size"
3380         done
3381         ll_sparseness_verify $myfn $GLOBALOFFSETS \
3382                             || error "ll_sparseness_verify $GLOBALOFFSETS"
3383         rm -f $myfn
3384       done
3385     done
3386 }
3387 run_test 44a "test sparse pwrite ==============================="
3388
3389 dirty_osc_total() {
3390         tot=0
3391         for d in `lctl get_param -n osc.*.cur_dirty_bytes`; do
3392                 tot=$(($tot + $d))
3393         done
3394         echo $tot
3395 }
3396 do_dirty_record() {
3397         before=`dirty_osc_total`
3398         echo executing "\"$*\""
3399         eval $*
3400         after=`dirty_osc_total`
3401         echo before $before, after $after
3402 }
3403 test_45() {
3404         [ $PARALLEL == "yes" ] && skip "skip parallel run" && return
3405         f="$DIR/f45"
3406         # Obtain grants from OST if it supports it
3407         echo blah > ${f}_grant
3408         stop_writeback
3409         sync
3410         do_dirty_record "echo blah > $f"
3411         [ $before -eq $after ] && error "write wasn't cached"
3412         do_dirty_record "> $f"
3413         [ $before -gt $after ] || error "truncate didn't lower dirty count"
3414         do_dirty_record "echo blah > $f"
3415         [ $before -eq $after ] && error "write wasn't cached"
3416         do_dirty_record "sync"
3417         [ $before -gt $after ] || error "writeback didn't lower dirty count"
3418         do_dirty_record "echo blah > $f"
3419         [ $before -eq $after ] && error "write wasn't cached"
3420         do_dirty_record "cancel_lru_locks osc"