Whamcloud - gitweb
6fec4c5d3c108248eb8a3ddb16b90abb23b0fedf
[fs/lustre-release.git] / lustre / tests / conf-sanity.sh
1 #!/bin/bash
2 # requirement:
3 #       add uml1 uml2 uml3 in your /etc/hosts
4
5 # FIXME - there is no reason to use all of these different
6 #   return codes, espcially when most of them are mapped to something
7 #   else anyway.  The combination of test number and return code
8 #   figure out what failed.
9
10 set -e
11
12 ONLY=${ONLY:-"$*"}
13
14 # These tests don't apply to mountconf
15 MOUNTCONFSKIP="10 11 12 13 13b 14 15"
16 # bug number for skipped test: 13739 
17 HEAD_EXCEPT="                  32a 32b "
18
19 # bug number for skipped test:                                 
20 ALWAYS_EXCEPT=" $CONF_SANITY_EXCEPT $MOUNTCONFSKIP $HEAD_EXCEPT"
21 # UPDATE THE COMMENT ABOVE WITH BUG NUMBERS WHEN CHANGING ALWAYS_EXCEPT!
22
23 SRCDIR=`dirname $0`
24 PATH=$PWD/$SRCDIR:$SRCDIR:$SRCDIR/../utils:$PATH
25
26 PTLDEBUG=${PTLDEBUG:--1}
27 SAVE_PWD=$PWD
28 LUSTRE=${LUSTRE:-`dirname $0`/..}
29 RLUSTRE=${RLUSTRE:-$LUSTRE}
30 MOUNTLUSTRE=${MOUNTLUSTRE:-/sbin/mount.lustre}
31 MKFSLUSTRE=${MKFSLUSTRE:-/usr/sbin/mkfs.lustre}
32 HOSTNAME=`hostname`
33
34 . $LUSTRE/tests/test-framework.sh
35 init_test_env $@
36 # STORED_MDSSIZE is used in test_18
37 if [ -n "$MDSSIZE" ]; then
38     STORED_MDSSIZE=$MDSSIZE
39 fi
40 # use small MDS + OST size to speed formatting time
41 MDSSIZE=40000
42 OSTSIZE=40000
43 . ${CONFIG:=$LUSTRE/tests/cfg/local.sh}
44
45 #
46 [ "$SLOW" = "no" ] && EXCEPT_SLOW="0 1 2 3 6 7 15 18 24b 25 30 31 32 33 34a "
47
48 assert_DIR
49
50 reformat() {
51         formatall
52 }
53
54 writeconf() {
55     local facet=mds
56     shift
57     stop ${facet} -f
58     rm -f ${facet}active
59     # who knows if/where $TUNEFS is installed?  Better reformat if it fails...
60     do_facet ${facet} "$TUNEFS --writeconf $MDSDEV" || echo "tunefs failed, reformatting instead" && reformat
61 }
62
63 gen_config() {
64         reformat
65         # The MGS must be started before the OSTs for a new fs, so start
66         # and stop to generate the startup logs. 
67         start_mds
68         start_ost
69         sleep 5
70         stop_ost
71         stop_mds
72 }
73
74 start_mds() {
75         echo "start mds service on `facet_active_host mds`"
76         start mds $MDSDEV $MDS_MOUNT_OPTS || return 94
77 }
78
79 stop_mds() {
80         echo "stop mds service on `facet_active_host mds`"
81         # These tests all use non-failover stop
82         stop mds -f  || return 97
83 }
84
85 start_ost() {
86         echo "start ost1 service on `facet_active_host ost1`"
87         start ost1 `ostdevname 1` $OST_MOUNT_OPTS || return 95
88 }
89
90 stop_ost() {
91         echo "stop ost1 service on `facet_active_host ost1`"
92         # These tests all use non-failover stop
93         stop ost1 -f  || return 98
94 }
95
96 start_ost2() {
97         echo "start ost2 service on `facet_active_host ost2`"
98         start ost2 `ostdevname 2` $OST_MOUNT_OPTS || return 92
99 }
100
101 stop_ost2() {
102         echo "stop ost2 service on `facet_active_host ost2`"
103         # These tests all use non-failover stop
104         stop ost2 -f  || return 93
105 }
106
107 mount_client() {
108         local MOUNTPATH=$1
109         echo "mount $FSNAME on ${MOUNTPATH}....."
110         zconf_mount `hostname` $MOUNTPATH  || return 96
111 }
112
113 remount_client() {
114         local SAVEMOUNTOPT=$MOUNTOPT
115         MOUNTOPT="remount,$1"
116         local MOUNTPATH=$2
117         echo "remount '$1' lustre on ${MOUNTPATH}....."
118         zconf_mount `hostname`  $MOUNTPATH  || return 96
119         MOUNTOPT=$SAVEMOUNTOPT
120 }
121
122 umount_client() {
123         local MOUNTPATH=$1
124         echo "umount lustre on ${MOUNTPATH}....."
125         zconf_umount `hostname` $MOUNTPATH || return 97
126 }
127
128 manual_umount_client(){
129         echo "manual umount lustre on ${MOUNT}...."
130         do_facet client "umount -d $MOUNT"
131 }
132
133 setup() {
134         start_ost
135         start_mds
136         mount_client $MOUNT
137 }
138
139 cleanup_nocli() {
140         stop_mds || return 201
141         stop_ost || return 202
142         unload_modules || return 203
143 }
144
145 cleanup() {
146         umount_client $MOUNT || return 200
147         cleanup_nocli || return $?
148 }
149
150 check_mount() {
151         do_facet client "cp /etc/passwd $DIR/a" || return 71
152         do_facet client "rm $DIR/a" || return 72
153         # make sure lustre is actually mounted (touch will block, 
154         # but grep won't, so do it after) 
155         do_facet client "grep $MOUNT' ' /proc/mounts > /dev/null" || return 73
156         echo "setup single mount lustre success"
157 }
158
159 check_mount2() {
160         do_facet client "touch $DIR/a" || return 71     
161         do_facet client "rm $DIR/a" || return 72        
162         do_facet client "touch $DIR2/a" || return 73    
163         do_facet client "rm $DIR2/a" || return 74       
164         echo "setup double mount lustre success"
165 }
166
167 build_test_filter
168
169 if [ "$ONLY" == "setup" ]; then
170         setup
171         exit
172 fi
173
174 if [ "$ONLY" == "cleanup" ]; then
175         cleanup
176         exit
177 fi
178
179 #create single point mountpoint
180
181 gen_config
182
183 init_gss
184
185 test_0() {
186         setup
187         check_mount || return 41
188         cleanup || return $?
189 }
190 run_test 0 "single mount setup"
191
192 test_1() {
193         start_ost
194         echo "start ost second time..."
195         setup
196         check_mount || return 42
197         cleanup || return $?
198 }
199 run_test 1 "start up ost twice (should return errors)"
200
201 test_2() {
202         start_ost
203         start_mds       
204         echo "start mds second time.."
205         start_mds
206         mount_client $MOUNT
207         check_mount || return 43
208         cleanup || return $?
209 }
210 run_test 2 "start up mds twice (should return err)"
211
212 test_3() {
213         setup
214         #mount.lustre returns an error if already in mtab
215         mount_client $MOUNT && return $?
216         check_mount || return 44
217         cleanup || return $?
218 }
219 run_test 3 "mount client twice (should return err)"
220
221 test_4() {
222         setup
223         touch $DIR/$tfile || return 85
224         stop_ost -f
225         cleanup
226         eno=$?
227         # ok for ost to fail shutdown
228         if [ 202 -ne $eno ]; then
229                 return $eno;
230         fi
231         return 0
232 }
233 run_test 4 "force cleanup ost, then cleanup"
234
235 test_5a() {     # was test_5
236         setup
237         touch $DIR/$tfile || return 1
238         fuser -m -v $MOUNT && echo "$MOUNT is in use by user space process."
239
240         stop_mds -f || return 2
241
242         # cleanup may return an error from the failed
243         # disconnects; for now I'll consider this successful
244         # if all the modules have unloaded.
245         umount -d $MOUNT &
246         UMOUNT_PID=$!
247         sleep 6
248         echo "killing umount"
249         kill -TERM $UMOUNT_PID
250         echo "waiting for umount to finish"
251         wait $UMOUNT_PID
252         if grep " $MOUNT " /proc/mounts; then
253                 echo "test 5: /proc/mounts after failed umount"
254                 umount $MOUNT &
255                 UMOUNT_PID=$!
256                 sleep 2
257                 echo "killing umount"
258                 kill -TERM $UMOUNT_PID
259                 echo "waiting for umount to finish"
260                 wait $UMOUNT_PID
261                 grep " $MOUNT " /proc/mounts && echo "test 5: /proc/mounts after second umount" && return 11
262         fi
263
264         manual_umount_client
265         # stop_mds is a no-op here, and should not fail
266         cleanup_nocli || return $?
267         # df may have lingering entry
268         manual_umount_client
269         # mtab may have lingering entry
270         local WAIT=0
271         local MAX_WAIT=20
272         local sleep=1
273         while [ "$WAIT" -ne "$MAX_WAIT" ]; do
274                 sleep $sleep
275                 grep -q $MOUNT" " /etc/mtab || break
276                 echo "Waiting /etc/mtab updated ... "
277                 WAIT=$(( WAIT + sleep))
278         done
279         [ "$WAIT" -eq "$MAX_WAIT" ] && error "/etc/mtab is not updated in $WAIT secs"
280         echo "/etc/mtab updated in $WAIT secs"
281 }
282 run_test 5a "force cleanup mds, then cleanup"
283
284 test_5b() {
285         start_ost
286         [ -d $MOUNT ] || mkdir -p $MOUNT
287         grep " $MOUNT " /etc/mtab && echo "test 5b: mtab before mount" && return 10
288         mount_client $MOUNT && return 1
289         grep " $MOUNT " /etc/mtab && echo "test 5b: mtab after failed mount" && return 11
290         umount_client $MOUNT    
291         # stop_mds is a no-op here, and should not fail
292         cleanup_nocli || return $?
293         return 0
294 }
295 run_test 5b "mds down, cleanup after failed mount (bug 2712) (should return errs)"
296
297 test_5c() {
298         start_ost
299         start_mds
300         [ -d $MOUNT ] || mkdir -p $MOUNT
301         grep " $MOUNT " /etc/mtab && echo "test 5c: mtab before mount" && return 10
302         local oldfs="${FSNAME}"
303         FSNAME="wrong.${FSNAME}"
304         mount_client $MOUNT || :
305         FSNAME=${oldfs}
306         grep " $MOUNT " /etc/mtab && echo "test 5c: mtab after failed mount" && return 11
307         umount_client $MOUNT
308         cleanup_nocli  || return $?
309 }
310 run_test 5c "cleanup after failed mount (bug 2712) (should return errs)"
311
312 test_5d() {
313         start_ost
314         start_mds
315         stop_ost -f
316         grep " $MOUNT " /etc/mtab && echo "test 5d: mtab before mount" && return 10
317         mount_client $MOUNT || return 1
318         cleanup  || return $?
319         grep " $MOUNT " /etc/mtab && echo "test 5d: mtab after unmount" && return 11
320         return 0
321 }
322 run_test 5d "mount with ost down"
323
324 test_5e() {
325         start_ost
326         start_mds
327
328 #define OBD_FAIL_PTLRPC_DELAY_SEND       0x506
329         do_facet client "lctl set_param fail_loc=0x80000506"
330         grep " $MOUNT " /etc/mtab && echo "test 5e: mtab before mount" && return 10
331         mount_client $MOUNT || echo "mount failed (not fatal)"
332         cleanup  || return $?
333         grep " $MOUNT " /etc/mtab && echo "test 5e: mtab after unmount" && return 11
334         return 0
335 }
336 run_test 5e "delayed connect, don't crash (bug 10268)"
337
338 test_6() {
339         setup
340         manual_umount_client
341         mount_client ${MOUNT} || return 87
342         touch $DIR/a || return 86
343         cleanup  || return $?
344 }
345 run_test 6 "manual umount, then mount again"
346
347 test_7() {
348         setup
349         manual_umount_client
350         cleanup_nocli || return $?
351 }
352 run_test 7 "manual umount, then cleanup"
353
354 test_8() {
355         setup
356         mount_client $MOUNT2
357         check_mount2 || return 45
358         umount_client $MOUNT2
359         cleanup  || return $?
360 }
361 run_test 8 "double mount setup"
362
363 test_9() {
364         start_ost
365
366         do_facet ost1 lctl set_param debug=\'inode trace\' || return 1
367         do_facet ost1 lctl set_param subsystem_debug=\'mds ost\' || return 1
368
369         CHECK_PTLDEBUG="`do_facet ost1 lctl get_param -n debug`"
370         if [ "$CHECK_PTLDEBUG" ] && [ "$CHECK_PTLDEBUG" = "trace inode" ];then
371            echo "lnet.debug success"
372         else
373            echo "lnet.debug: want 'trace inode', have '$CHECK_PTLDEBUG'"
374            return 1
375         fi
376         CHECK_SUBSYS="`do_facet ost1 lctl get_param -n subsystem_debug`"
377         if [ "$CHECK_SUBSYS" ] && [ "$CHECK_SUBSYS" = "mds ost" ]; then
378            echo "lnet.subsystem_debug success"
379         else
380            echo "lnet.subsystem_debug: want 'mds ost', have '$CHECK_SUBSYS'"
381            return 1
382         fi
383         stop_ost || return $?
384 }
385
386 run_test 9 "test ptldebug and subsystem for mkfs"
387
388 test_10() {
389         echo "generate configuration with the same name for node and mds"
390         OLDXMLCONFIG=$XMLCONFIG
391         XMLCONFIG="broken.xml"
392         [ -f "$XMLCONFIG" ] && rm -f $XMLCONFIG
393         facet="mds"
394         rm -f ${facet}active
395         add_facet $facet
396         echo "the name for node and mds is the same"
397         do_lmc --add mds --node ${facet}_facet --mds ${facet}_facet \
398             --dev $MDSDEV --size $MDSSIZE || return $?
399         do_lmc --add lov --mds ${facet}_facet --lov lov1 --stripe_sz \
400             $STRIPE_BYTES --stripe_cnt $STRIPES_PER_OBJ \
401             --stripe_pattern 0 || return $?
402         add_ost ost --lov lov1 --dev $OSTDEV --size $OSTSIZE
403         facet="client"
404         add_facet $facet --lustre_upcall $UPCALL
405         do_lmc --add mtpt --node ${facet}_facet --mds mds_facet \
406             --lov lov1 --path $MOUNT
407
408         echo "mount lustre"
409         start_ost
410         start_mds
411         mount_client $MOUNT
412         check_mount || return 41
413         cleanup || return $?
414
415         echo "Success!"
416         XMLCONFIG=$OLDXMLCONFIG
417 }
418 run_test 10 "mount lustre with the same name for node and mds"
419
420 test_11() {
421         OLDXMLCONFIG=$XMLCONFIG
422         XMLCONFIG="conf11.xml"
423
424         [ -f "$XMLCONFIG" ] && rm -f $XMLCONFIG
425         add_mds mds --dev $MDSDEV --size $MDSSIZE
426         add_ost ost --dev $OSTDEV --size $OSTSIZE
427         add_client client mds --path $MOUNT --ost ost_svc || return $?
428         echo "Default lov config success!"
429
430         [ -f "$XMLCONFIG" ] && rm -f $XMLCONFIG
431         add_mds mds --dev $MDSDEV --size $MDSSIZE
432         add_ost ost --dev $OSTDEV --size $OSTSIZE
433         add_client client mds --path $MOUNT && return $?
434         echo "--add mtpt with neither --lov nor --ost will return error"
435
436         echo ""
437         echo "Success!"
438         XMLCONFIG=$OLDXMLCONFIG
439 }
440 run_test 11 "use default lov configuration (should return error)"
441
442 test_12() {
443         OLDXMLCONFIG=$XMLCONFIG
444         XMLCONFIG="batch.xml"
445         BATCHFILE="batchfile"
446
447         # test double quote
448         [ -f "$XMLCONFIG" ] && rm -f $XMLCONFIG
449         [ -f "$BATCHFILE" ] && rm -f $BATCHFILE
450         echo "--add net --node $HOSTNAME --nid $HOSTNAME --nettype tcp" > $BATCHFILE
451         echo "--add mds --node $HOSTNAME --mds mds1 --mkfsoptions \"-I 128\"" >> $BATCHFILE
452         # --mkfsoptions "-I 128"
453         do_lmc -m $XMLCONFIG --batch $BATCHFILE || return $?
454         if [ `sed -n '/>-I 128</p' $XMLCONFIG | wc -l` -eq 1 ]; then
455                 echo "matched double quote success"
456         else
457                 echo "matched double quote fail"
458                 return 1
459         fi
460         rm -f $XMLCONFIG
461         rm -f $BATCHFILE
462         echo "--add net --node $HOSTNAME --nid $HOSTNAME --nettype tcp" > $BATCHFILE
463         echo "--add mds --node $HOSTNAME --mds mds1 --mkfsoptions \"-I 128" >> $BATCHFILE
464         # --mkfsoptions "-I 128
465         do_lmc -m $XMLCONFIG --batch $BATCHFILE && return $?
466         echo "unmatched double quote should return error"
467
468         # test single quote
469         rm -f $BATCHFILE
470         echo "--add net --node $HOSTNAME --nid $HOSTNAME --nettype tcp" > $BATCHFILE
471         echo "--add mds --node $HOSTNAME --mds mds1 --mkfsoptions '-I 128'" >> $BATCHFILE
472         # --mkfsoptions '-I 128'
473         do_lmc -m $XMLCONFIG --batch $BATCHFILE || return $?
474         if [ `sed -n '/>-I 128</p' $XMLCONFIG | wc -l` -eq 1 ]; then
475                 echo "matched single quote success"
476         else
477                 echo "matched single quote fail"
478                 return 1
479         fi
480         rm -f $XMLCONFIG
481         rm -f $BATCHFILE
482         echo "--add net --node $HOSTNAME --nid $HOSTNAME --nettype tcp" > $BATCHFILE
483         echo "--add mds --node $HOSTNAME --mds mds1 --mkfsoptions '-I 128" >> $BATCHFILE
484         # --mkfsoptions '-I 128
485         do_lmc -m $XMLCONFIG --batch $BATCHFILE && return $?
486         echo "unmatched single quote should return error"
487
488         # test backslash
489         rm -f $BATCHFILE
490         echo "--add net --node $HOSTNAME --nid $HOSTNAME --nettype tcp" > $BATCHFILE
491         echo "--add mds --node $HOSTNAME --mds mds1 --mkfsoptions \-\I\ \128" >> $BATCHFILE
492         # --mkfsoptions \-\I\ \128
493         do_lmc -m $XMLCONFIG --batch $BATCHFILE || return $?
494         if [ `sed -n '/>-I 128</p' $XMLCONFIG | wc -l` -eq 1 ]; then
495                 echo "backslash followed by a whitespace/letter success"
496         else
497                 echo "backslash followed by a whitespace/letter fail"
498                 return 1
499         fi
500         rm -f $XMLCONFIG
501         rm -f $BATCHFILE
502         echo "--add net --node $HOSTNAME --nid $HOSTNAME --nettype tcp" > $BATCHFILE
503         echo "--add mds --node $HOSTNAME --mds mds1 --mkfsoptions -I\ 128\\" >> $BATCHFILE
504         # --mkfsoptions -I\ 128\
505         do_lmc -m $XMLCONFIG --batch $BATCHFILE && return $?
506         echo "backslash followed by nothing should return error"
507
508         rm -f $BATCHFILE
509         XMLCONFIG=$OLDXMLCONFIG
510 }
511 run_test 12 "lmc --batch, with single/double quote, backslash in batchfile"
512
513 test_13a() {    # was test_13
514         OLDXMLCONFIG=$XMLCONFIG
515         XMLCONFIG="conf13-1.xml"
516
517         # check long uuid will be truncated properly and uniquely
518         echo "To generate XML configuration file(with long ost name): $XMLCONFIG"
519         [ -f "$XMLCONFIG" ] && rm -f $XMLCONFIG
520         do_lmc --add net --node $HOSTNAME --nid $HOSTNAME --nettype tcp
521         do_lmc --add mds --node $HOSTNAME --mds mds1_name_longer_than_31characters
522         do_lmc --add mds --node $HOSTNAME --mds mds2_name_longer_than_31characters
523         if [ ! -f "$XMLCONFIG" ]; then
524                 echo "Error:no file $XMLCONFIG created!"
525                 return 1
526         fi
527         EXPECTEDMDS1UUID="e_longer_than_31characters_UUID"
528         EXPECTEDMDS2UUID="longer_than_31characters_UUID_2"
529         FOUNDMDS1UUID=`awk -F"'" '/<mds .*uuid=/' $XMLCONFIG | sed -n '1p' \
530                        | sed "s/ /\n\r/g" | awk -F"'" '/uuid=/{print $2}'`
531         FOUNDMDS2UUID=`awk -F"'" '/<mds .*uuid=/' $XMLCONFIG | sed -n '2p' \
532                        | sed "s/ /\n\r/g" | awk -F"'" '/uuid=/{print $2}'`
533         [ -z "$FOUNDMDS1UUID" ] && echo "MDS1 UUID empty" && return 1
534         [ -z "$FOUNDMDS2UUID" ] && echo "MDS2 UUID empty" && return 1
535         if ([ $EXPECTEDMDS1UUID = $FOUNDMDS1UUID ] && [ $EXPECTEDMDS2UUID = $FOUNDMDS2UUID ]) || \
536            ([ $EXPECTEDMDS1UUID = $FOUNDMDS2UUID ] && [ $EXPECTEDMDS2UUID = $FOUNDMDS1UUID ]); then
537                 echo "Success:long uuid truncated successfully and being unique."
538         else
539                 echo "Error:expected uuid for mds1 and mds2: $EXPECTEDMDS1UUID; $EXPECTEDMDS2UUID"
540                 echo "but:     found uuid for mds1 and mds2: $FOUNDMDS1UUID; $FOUNDMDS2UUID"
541                 return 1
542         fi
543         rm -f $XMLCONFIG
544         XMLCONFIG=$OLDXMLCONFIG
545 }
546 run_test 13a "check new_uuid of lmc operating correctly"
547
548 test_13b() {
549         OLDXMLCONFIG=$XMLCONFIG
550         XMLCONFIG="conf13-1.xml"
551         SECONDXMLCONFIG="conf13-2.xml"
552         # check multiple invocations for lmc generate same XML configuration file
553         rm -f $XMLCONFIG
554         echo "Generate the first XML configuration file"
555         gen_config
556         echo "mv $XMLCONFIG to $SECONDXMLCONFIG"
557         sed -e "s/mtime[^ ]*//" $XMLCONFIG > $SECONDXMLCONFIG || return $?
558         echo "Generate the second XML configuration file"
559         gen_config
560         # don't compare .xml mtime, it will always be different
561         if [ `sed -e "s/mtime[^ ]*//" $XMLCONFIG | diff - $SECONDXMLCONFIG | wc -l` -eq 0 ]; then
562                 echo "Success:multiple invocations for lmc generate same XML file"
563         else
564                 echo "Error: multiple invocations for lmc generate different XML file"
565                 return 1
566         fi
567
568         rm -f $XMLCONFIG $SECONDXMLCONFIG
569         XMLCONFIG=$OLDXMLCONFIG
570 }
571 run_test 13b "check lmc generates consistent .xml file"
572
573 test_14() {
574         rm -f $XMLCONFIG
575
576         # create xml file with --mkfsoptions for ost
577         echo "create xml file with --mkfsoptions for ost"
578         add_mds mds --dev $MDSDEV --size $MDSSIZE
579         add_lov lov1 mds --stripe_sz $STRIPE_BYTES\
580             --stripe_cnt $STRIPES_PER_OBJ --stripe_pattern 0
581         add_ost ost --lov lov1 --dev $OSTDEV --size $OSTSIZE \
582             --mkfsoptions "-Llabel_conf_14"
583         add_client client mds --lov lov1 --path $MOUNT
584
585         FOUNDSTRING=`awk -F"<" '/<mkfsoptions>/{print $2}' $XMLCONFIG`
586         EXPECTEDSTRING="mkfsoptions>-Llabel_conf_14"
587         if [ "$EXPECTEDSTRING" != "$FOUNDSTRING" ]; then
588                 echo "Error: expected: $EXPECTEDSTRING; found: $FOUNDSTRING"
589                 return 1
590         fi
591         echo "Success:mkfsoptions for ost written to xml file correctly."
592
593         # mount lustre to test lconf mkfsoptions-parsing
594         echo "mount lustre"
595         start_ost
596         start_mds
597         mount_client $MOUNT || return $?
598         if [ -z "`do_facet ost1 dumpe2fs -h $OSTDEV | grep label_conf_14`" ]; then
599                 echo "Error: the mkoptions not applied to mke2fs of ost."
600                 return 1
601         fi
602         cleanup
603         echo "lconf mkfsoptions for ost success"
604
605         gen_config
606 }
607 run_test 14 "test mkfsoptions of ost for lmc and lconf"
608
609 cleanup_15() {
610         trap 0
611         [ -f $MOUNTLUSTRE ] && echo "remove $MOUNTLUSTRE" && rm -f $MOUNTLUSTRE
612         if [ -f $MOUNTLUSTRE.sav ]; then
613                 echo "return original $MOUNTLUSTRE.sav to $MOUNTLUSTRE"
614                 mv $MOUNTLUSTRE.sav $MOUNTLUSTRE
615         fi
616 }
617
618 # this only tests the kernel mount command, not anything about lustre.
619 test_15() {
620         MOUNTLUSTRE=${MOUNTLUSTRE:-/sbin/mount.lustre}
621         start_ost
622         start_mds
623
624         echo "mount lustre on ${MOUNT} without $MOUNTLUSTRE....."
625         if [ -f "$MOUNTLUSTRE" ]; then
626                 echo "save $MOUNTLUSTRE to $MOUNTLUSTRE.sav"
627                 mv $MOUNTLUSTRE $MOUNTLUSTRE.sav && trap cleanup_15 EXIT INT
628                 if [ -f $MOUNTLUSTRE ]; then
629                         skip "$MOUNTLUSTRE cannot be moved, skipping test"
630                         return 0
631                 fi
632         fi
633
634         mount_client $MOUNT && error "mount succeeded" && return 1
635         echo "mount lustre on $MOUNT without $MOUNTLUSTRE failed as expected"
636         cleanup_15
637         cleanup || return $?
638 }
639 run_test 15 "zconf-mount without /sbin/mount.lustre (should return error)"
640
641 # LOGS/PENDING do not exist anymore since CMD3
642 test_16() {
643         TMPMTPT="${TMP}/conf16"
644
645         if [ ! -e "$MDSDEV" ]; then
646             log "no $MDSDEV existing, so mount Lustre to create one"
647             setup
648             check_mount || return 41
649             cleanup || return $?
650         fi
651
652         [ -f "$MDSDEV" ] && LOOPOPT="-o loop"
653
654         log "change the mode of $MDSDEV/OBJECTS to 555"
655         do_facet mds "mkdir -p $TMPMTPT &&
656                       mount $LOOPOPT -t $FSTYPE $MDSDEV $TMPMTPT &&
657                       chmod 555 $TMPMTPT/OBJECTS &&
658                       umount $TMPMTPT" || return $?
659
660         log "mount Lustre to change the mode of OBJECTS, then umount Lustre"
661         setup
662         check_mount || return 41
663         cleanup || return $?
664
665         log "read the mode of OBJECTS and check if they has been changed properly"
666         EXPECTEDOBJECTSMODE=`do_facet mds "debugfs -R 'stat OBJECTS' $MDSDEV 2> /dev/null" | grep 'Mode: ' | sed -e "s/.*Mode: *//" -e "s/ *Flags:.*//"`
667
668         if [ "$EXPECTEDOBJECTSMODE" = "0777" ]; then
669                 log "Success:Lustre change the mode of OBJECTS correctly"
670         else
671                 error "Lustre does not change mode of OBJECTS properly"
672         fi
673 }
674 run_test 16 "verify that lustre will correct the mode of OBJECTS"
675
676 test_17() {
677         if [ ! -e "$MDSDEV" ]; then
678             echo "no $MDSDEV existing, so mount Lustre to create one"
679             setup
680             check_mount || return 41
681             cleanup || return $?
682         fi
683
684         echo "Remove mds config log"
685         do_facet mds "debugfs -w -R 'unlink CONFIGS/$FSNAME-MDT0000' $MDSDEV || return \$?" || return $?
686
687         start_ost
688         start_mds && return 42
689         gen_config
690 }
691 run_test 17 "Verify failed mds_postsetup won't fail assertion (2936) (should return errs)"
692
693 test_18() {
694         [ "$FSTYPE" != "ldiskfs" ] && skip "not needed for FSTYPE=$FSTYPE" && return
695
696         local MIN=2000000
697
698         local OK=
699         # check if current MDSSIZE is large enough
700         [ $MDSSIZE -ge $MIN ] && OK=1 && myMDSSIZE=$MDSSIZE && \
701                 log "use MDSSIZE=$MDSSIZE"
702
703         # check if the global config has a large enough MDSSIZE
704         [ -z "$OK" -a ! -z "$STORED_MDSSIZE" ] && [ $STORED_MDSSIZE -ge $MIN ] && \
705                 OK=1 && myMDSSIZE=$STORED_MDSSIZE && \
706                 log "use STORED_MDSSIZE=$STORED_MDSSIZE"
707
708         # check if the block device is large enough
709         [ -z "$OK" -a -b $MDSDEV ] && \
710                 [ "$(dd if=$MDSDEV of=/dev/null bs=1k count=1 skip=$MIN 2>&1 |
711                      awk '($3 == "in") { print $1 }')" = "1+0" ] && OK=1 && \
712                 myMDSSIZE=$MIN && log "use device $MDSDEV with MIN=$MIN"
713
714         # check if a loopback device has enough space for fs metadata (5%)
715         [ -z "$OK" ] && [ -f $MDSDEV -o ! -e $MDSDEV ] &&
716                 SPACE=$(df -P $(dirname $MDSDEV) |
717                         awk '($1 != "Filesystem") {print $4}') &&
718                 [ $SPACE -gt $((MIN / 20)) ] && OK=1 && myMDSSIZE=$MIN && \
719                         log "use file $MDSDEV with MIN=$MIN"
720
721         [ -z "$OK" ] && skip "$MDSDEV too small for ${MIN}kB MDS" && return
722
723
724         echo "mount mds with large journal..."
725         local OLD_MDS_MKFS_OPTS=$MDS_MKFS_OPTS
726
727         MDS_MKFS_OPTS="--mgs --mdt --fsname=$FSNAME --device-size=$myMDSSIZE --param sys.timeout=$TIMEOUT $MDSOPT"
728
729         gen_config
730         echo "mount lustre system..."
731         setup
732         check_mount || return 41
733
734         echo "check journal size..."
735         local FOUNDSIZE=`do_facet mds "debugfs -c -R 'stat <8>' $MDSDEV" | awk '/Size: / { print $NF; exit;}'`
736         if [ $FOUNDSIZE -gt $((32 * 1024 * 1024)) ]; then
737                 log "Success: mkfs creates large journals. Size: $((FOUNDSIZE >> 20))M"
738         else
739                 error "expected journal size > 32M, found $((FOUNDSIZE >> 20))M"
740         fi
741
742         cleanup || return $?
743
744         MDS_MKFS_OPTS=$OLD_MDS_MKFS_OPTS
745         gen_config
746 }
747 run_test 18 "check mkfs creates large journals"
748
749 test_19a() {
750         start_mds || return 1
751         stop_mds -f || return 2
752 }
753 run_test 19a "start/stop MDS without OSTs"
754
755 test_19b() {
756         start_ost || return 1
757         stop_ost -f || return 2
758 }
759 run_test 19b "start/stop OSTs without MDS"
760
761 test_20() {
762         # first format the ost/mdt
763         start_ost
764         start_mds
765         mount_client $MOUNT
766         check_mount || return 43
767         rm -f $DIR/$tfile
768         remount_client ro $MOUNT || return 44
769         touch $DIR/$tfile && echo "$DIR/$tfile created incorrectly" && return 45
770         [ -e $DIR/$tfile ] && echo "$DIR/$tfile exists incorrectly" && return 46
771         remount_client rw $MOUNT || return 47
772         touch $DIR/$tfile
773         [ ! -f $DIR/$tfile ] && echo "$DIR/$tfile missing" && return 48
774         MCNT=`grep -c $MOUNT /etc/mtab`
775         [ "$MCNT" -ne 1 ] && echo "$MOUNT in /etc/mtab $MCNT times" && return 49
776         umount_client $MOUNT
777         stop_mds
778         stop_ost
779 }
780 run_test 20 "remount ro,rw mounts work and doesn't break /etc/mtab"
781
782 test_21a() {
783         start_mds
784         start_ost
785         stop_ost
786         stop_mds
787 }
788 run_test 21a "start mds before ost, stop ost first"
789
790 test_21b() {
791         start_ost
792         start_mds
793         stop_mds
794         stop_ost
795 }
796 run_test 21b "start ost before mds, stop mds first"
797
798 test_21c() {
799         start_ost
800         start_mds
801         start_ost2
802         stop_ost
803         stop_ost2
804         stop_mds
805 }
806 run_test 21c "start mds between two osts, stop mds last"
807
808 test_22() {
809         #reformat to remove all logs
810         reformat
811         start_mds
812         echo Client mount before any osts are in the logs
813         mount_client $MOUNT
814         check_mount && return 41
815         pass
816
817         echo Client mount with ost in logs, but none running
818         start_ost
819         stop_ost
820         mount_client $MOUNT
821         # check_mount will block trying to contact ost
822         umount_client $MOUNT
823         pass
824
825         echo Client mount with a running ost
826         start_ost
827         if $GSS; then
828                 # if gss enabled, wait full time to let connection from
829                 # mds to ost be established, due to the mismatch between
830                 # initial connect timeout and gss context negotiation timeout.
831                 # This perhaps could be remove after AT landed.
832                 echo "sleep $((TIMEOUT + TIMEOUT + TIMEOUT))s"
833                 sleep $((TIMEOUT + TIMEOUT + TIMEOUT))
834         fi
835         mount_client $MOUNT
836         check_mount || return 41
837         pass
838
839         cleanup
840 }
841 run_test 22 "start a client before osts (should return errs)"
842
843 test_23a() {    # was test_23
844         setup
845         # fail mds
846         stop mds   
847         # force down client so that recovering mds waits for reconnect
848         local running=$(grep -c $MOUNT /proc/mounts) || true
849         if [ $running -ne 0 ]; then
850                 echo "Stopping client $MOUNT (opts: -f)"
851                 umount -f $MOUNT
852         fi
853
854         # enter recovery on mds
855         start_mds
856         # try to start a new client
857         mount_client $MOUNT &
858         sleep 5
859         MOUNT_PID=$(ps -ef | grep "t lustre" | grep -v grep | awk '{print $2}')
860         MOUNT_LUSTRE_PID=`ps -ef | grep mount.lustre | grep -v grep | awk '{print $2}'`
861         echo mount pid is ${MOUNT_PID}, mount.lustre pid is ${MOUNT_LUSTRE_PID}
862         ps --ppid $MOUNT_PID
863         ps --ppid $MOUNT_LUSTRE_PID
864         # FIXME why o why can't I kill these? Manual "ctrl-c" works...
865         kill -TERM $MOUNT_LUSTRE_PID
866         echo "waiting for mount to finish"
867         ps -ef | grep mount
868         # we can not wait $MOUNT_PID because it is not a child of this shell
869         local PID1
870         local PID2
871         local WAIT=0
872         local MAX_WAIT=20
873         local sleep=1
874         while [ "$WAIT" -lt "$MAX_WAIT" ]; do
875                 sleep $sleep
876                 PID1=$(ps -ef | awk '{print $2}' | grep -w $MOUNT_PID)
877                 PID2=$(ps -ef | awk '{print $2}' | grep -w $MOUNT_LUSTRE_PID)
878                 echo PID1=$PID1
879                 echo PID2=$PID2
880                 [ -z "$PID1" -a -z "$PID2" ] && break
881                 echo "waiting for mount to finish ... "
882                 WAIT=$(( WAIT + sleep))
883         done
884         [ "$WAIT" -eq "$MAX_WAIT" ] && error "MOUNT_PID $MOUNT_PID and \
885                 MOUNT__LUSTRE_PID $MOUNT__LUSTRE_PID still not killed in $WAIT secs"
886         ps -ef | grep mount
887         stop_mds || error
888         stop_ost || error
889 }
890 run_test 23a "interrupt client during recovery mount delay"
891
892 umount_client $MOUNT
893 cleanup_nocli
894
895 test_23b() {    # was test_23
896         start_ost
897         start_mds
898         # Simulate -EINTR during mount OBD_FAIL_LDLM_CLOSE_THREAD
899         lctl set_param fail_loc=0x80000313
900         mount_client $MOUNT
901         cleanup
902 }
903 run_test 23b "Simulate -EINTR during mount"
904
905 fs2mds_HOST=$mds_HOST
906 fs2ost_HOST=$ost_HOST
907
908 cleanup_24a() {
909         trap 0
910         echo "umount $MOUNT2 ..."
911         umount $MOUNT2 || true
912         echo "stopping fs2mds ..."
913         stop fs2mds -f || true
914         echo "stopping fs2ost ..."
915         stop fs2ost -f || true
916 }
917
918 test_24a() {
919         #set up fs1 
920         gen_config
921         #set up fs2
922         [ -n "$ost1_HOST" ] && fs2ost_HOST=$ost1_HOST
923         if [ -z "$fs2ost_DEV" -o -z "$fs2mds_DEV" ]; then
924                 do_facet $SINGLEMDS [ -b "$MDSDEV" ] && \
925                 skip "mixed loopback and real device not working" && return
926         fi
927
928         local fs2mdsdev=${fs2mds_DEV:-${MDSDEV}_2}
929         local fs2ostdev=${fs2ost_DEV:-$(ostdevname 1)_2}
930
931         # test 8-char fsname as well
932         local FSNAME2=test1234
933         add fs2mds $MDS_MKFS_OPTS --fsname=${FSNAME2} --nomgs --mgsnode=$MGSNID --reformat $fs2mdsdev || exit 10
934
935         add fs2ost $OST_MKFS_OPTS --fsname=${FSNAME2} --reformat $fs2ostdev || exit 10
936
937         setup
938         start fs2mds $fs2mdsdev $MDS_MOUNT_OPTS && trap cleanup_24a EXIT INT
939         start fs2ost $fs2ostdev $OST_MOUNT_OPTS
940         mkdir -p $MOUNT2
941         mount -t lustre $MGSNID:/${FSNAME2} $MOUNT2 || return 1
942         # 1 still works
943         check_mount || return 2
944         # files written on 1 should not show up on 2
945         cp /etc/passwd $DIR/$tfile
946         sleep 10
947         [ -e $MOUNT2/$tfile ] && error "File bleed" && return 7
948         # 2 should work
949         sleep 5
950         cp /etc/passwd $MOUNT2/b || return 3
951         rm $MOUNT2/b || return 4
952         # 2 is actually mounted
953         grep $MOUNT2' ' /proc/mounts > /dev/null || return 5
954         # failover 
955         facet_failover fs2mds
956         facet_failover fs2ost
957         df
958         umount_client $MOUNT 
959         # the MDS must remain up until last MDT
960         stop_mds
961         MDS=$(do_facet $SINGLEMDS "lctl get_param -n devices" | awk '($3 ~ "mdt" && $4 ~ "MDT") { print $4 }')
962         [ -z "$MDS" ] && error "No MDT" && return 8
963         cleanup_24a
964         cleanup_nocli || return 6
965 }
966 run_test 24a "Multiple MDTs on a single node"
967
968 test_24b() {
969         if [ -z "$fs2mds_DEV" ]; then
970                 do_facet $SINGLEMDS [ -b "$MDSDEV" ] && \
971                 skip "mixed loopback and real device not working" && return
972         fi
973
974         local fs2mdsdev=${fs2mds_DEV:-${MDSDEV}_2}
975
976         add fs2mds $MDS_MKFS_OPTS --fsname=${FSNAME}2 --mgs --reformat $fs2mdsdev || exit 10 
977         setup
978         start fs2mds $fs2mdsdev $MDS_MOUNT_OPTS && return 2
979         cleanup || return 6
980 }
981 run_test 24b "Multiple MGSs on a single node (should return err)"
982
983 test_25() {
984         setup
985         check_mount || return 2
986         local MODULES=$($LCTL modules | awk '{ print $2 }')
987         rmmod $MODULES 2>/dev/null || true
988         cleanup || return 6
989 }
990 run_test 25 "Verify modules are referenced"
991
992 test_26() {
993     load_modules
994     # we need modules before mount for sysctl, so make sure...
995     do_facet mds "lsmod | grep -q lustre || modprobe lustre"
996 #define OBD_FAIL_MDS_FS_SETUP            0x135
997     do_facet mds "lctl set_param fail_loc=0x80000135"
998     start_mds && echo MDS started && return 1
999     lctl get_param -n devices
1000     DEVS=$(lctl get_param -n devices | wc -l)
1001     [ $DEVS -gt 0 ] && return 2
1002     unload_modules || return 203
1003 }
1004 run_test 26 "MDT startup failure cleans LOV (should return errs)"
1005
1006 set_and_check() {
1007         local myfacet=$1
1008         local TEST=$2
1009         local PARAM=$3
1010         local ORIG=$(do_facet $myfacet "$TEST") 
1011         if [ $# -gt 3 ]; then
1012             local FINAL=$4
1013         else
1014             local -i FINAL
1015             FINAL=$(($ORIG + 5))
1016         fi
1017         echo "Setting $PARAM from $ORIG to $FINAL"
1018         do_facet mds "$LCTL conf_param $PARAM=$FINAL" || error conf_param failed
1019         local RESULT
1020         local MAX=90
1021         local WAIT=0
1022         while [ 1 ]; do
1023             sleep 5
1024             RESULT=$(do_facet $myfacet "$TEST") 
1025             if [ $RESULT -eq $FINAL ]; then
1026                 echo "Updated config after $WAIT sec (got $RESULT)"
1027                 break
1028             fi
1029             WAIT=$((WAIT + 5))
1030             if [ $WAIT -eq $MAX ]; then
1031                 echo "Config update not seen: wanted $FINAL got $RESULT"
1032                 return 3
1033             fi
1034             echo "Waiting $(($MAX - $WAIT)) secs for config update" 
1035         done
1036 }
1037
1038 test_27a() {
1039         start_ost || return 1
1040         start_mds || return 2
1041         echo "Requeue thread should have started: " 
1042         ps -e | grep ll_cfg_requeue 
1043         set_and_check ost1 "lctl get_param -n obdfilter.$FSNAME-OST0000.client_cache_seconds" "$FSNAME-OST0000.ost.client_cache_seconds" || return 3
1044         cleanup_nocli
1045 }
1046 run_test 27a "Reacquire MGS lock if OST started first"
1047
1048 test_27b() {
1049         setup
1050         facet_failover mds
1051         set_and_check mds "lctl get_param -n mdt.$FSNAME-MDT0000.identity_acquire_expire" "$FSNAME-MDT0000.mdt.identity_acquire_expire" || return 3
1052         set_and_check client "lctl get_param -n mdc.$FSNAME-MDT0000-mdc-*.max_rpcs_in_flight" "$FSNAME-MDT0000.mdc.max_rpcs_in_flight" || return 4
1053         check_mount
1054         cleanup
1055 }
1056 run_test 27b "Reacquire MGS lock after failover"
1057
1058 test_28() {
1059         setup
1060         TEST="lctl get_param -n llite.$FSNAME-*.max_read_ahead_whole_mb"
1061         PARAM="$FSNAME.llite.max_read_ahead_whole_mb"
1062         ORIG=$($TEST)
1063         FINAL=$(($ORIG + 1))
1064         set_and_check client "$TEST" "$PARAM" $FINAL || return 3
1065         FINAL=$(($FINAL + 1))
1066         set_and_check client "$TEST" "$PARAM" $FINAL || return 4
1067         umount_client $MOUNT || return 200
1068         mount_client $MOUNT
1069         RESULT=$($TEST)
1070         if [ $RESULT -ne $FINAL ]; then
1071             echo "New config not seen: wanted $FINAL got $RESULT"
1072             return 4
1073         else
1074             echo "New config success: got $RESULT"
1075         fi
1076         set_and_check client "$TEST" "$PARAM" $ORIG || return 5
1077         cleanup
1078 }
1079 run_test 28 "permanent parameter setting"
1080
1081 test_29() {
1082         [ "$OSTCOUNT" -lt "2" ] && skip "$OSTCOUNT < 2, skipping" && return
1083         setup > /dev/null 2>&1
1084         start_ost2
1085         sleep 10
1086
1087         local PARAM="$FSNAME-OST0001.osc.active"
1088         local PROC_ACT="osc.$FSNAME-OST0001-osc-[^M]*.active"
1089         local PROC_UUID="osc.$FSNAME-OST0001-osc-[^M]*.ost_server_uuid"
1090
1091         ACTV=$(lctl get_param -n $PROC_ACT)
1092         DEAC=$((1 - $ACTV))
1093         set_and_check client "lctl get_param -n $PROC_ACT" "$PARAM" $DEAC || return 2
1094         # also check ost_server_uuid status
1095         RESULT=$(lctl get_param -n $PROC_UUID | grep DEACTIV)
1096         if [ -z "$RESULT" ]; then
1097             echo "Live client not deactivated: $(lctl get_param -n $PROC_UUID)"
1098             return 3
1099         else
1100             echo "Live client success: got $RESULT"
1101         fi
1102
1103         # check MDT too 
1104         local MPROC="osc.$FSNAME-OST0001-osc-[M]*.active"
1105         local MAX=30
1106         local WAIT=0
1107         while [ 1 ]; do
1108             sleep 5
1109             RESULT=`do_facet mds " lctl get_param -n $MPROC"`
1110             [ ${PIPESTATUS[0]} = 0 ] || error "Can't read $MPROC"
1111             if [ $RESULT -eq $DEAC ]; then
1112                 echo "MDT deactivated also after $WAIT sec (got $RESULT)"
1113                 break
1114             fi
1115             WAIT=$((WAIT + 5))
1116             if [ $WAIT -eq $MAX ]; then
1117                 echo "MDT not deactivated: wanted $DEAC got $RESULT"
1118                 return 4
1119             fi
1120             echo "Waiting $(($MAX - $WAIT)) secs for MDT deactivated"
1121         done
1122
1123         # test new client starts deactivated
1124         umount_client $MOUNT || return 200
1125         mount_client $MOUNT
1126         RESULT=$(lctl get_param -n $PROC_UUID | grep DEACTIV | grep NEW)
1127         if [ -z "$RESULT" ]; then
1128             echo "New client not deactivated from start: $(lctl get_param -n $PROC_UUID)"
1129             return 5
1130         else
1131             echo "New client success: got $RESULT"
1132         fi
1133
1134         # make sure it reactivates
1135         set_and_check client "lctl get_param -n $PROC_ACT" "$PARAM" $ACTV || return 6
1136
1137         umount_client $MOUNT
1138         stop_ost2
1139         cleanup_nocli
1140         #writeconf to remove all ost2 traces for subsequent tests
1141         writeconf
1142         start_mds
1143         start_ost
1144         cleanup
1145 }
1146 run_test 29 "permanently remove an OST"
1147
1148 test_30() {
1149         setup
1150
1151         TEST="lctl get_param -n llite.$FSNAME-*.max_read_ahead_whole_mb"
1152         ORIG=$($TEST)
1153         LIST=(1 2 3 4 5 4 3 2 1 2 3 4 5 4 3 2 1 2 3 4 5)
1154         for i in ${LIST[@]}; do
1155             set_and_check client "$TEST" "$FSNAME.llite.max_read_ahead_whole_mb" $i || return 3
1156         done
1157         # make sure client restart still works 
1158         umount_client $MOUNT
1159         mount_client $MOUNT || return 4
1160         [ "$($TEST)" -ne "$i" ] && return 5   
1161         set_and_check client "$TEST" "$FSNAME.llite.max_read_ahead_whole_mb" $ORIG || return 6
1162         cleanup
1163 }
1164 run_test 30 "Big config llog"
1165
1166 test_31() { # bug 10734
1167         # ipaddr must not exist
1168         mount -t lustre 4.3.2.1@tcp:/lustre $MOUNT || true
1169         cleanup
1170 }
1171 run_test 31 "Connect to non-existent node (shouldn't crash)"
1172
1173 test_32a() {
1174         # XXX - make this run on client-only systems with real hardware on
1175         #       the OST and MDT
1176         #       there appears to be a lot of assumption here about loopback
1177         #       devices
1178         # or maybe this test is just totally useless on a client-only system
1179         [ "$NETTYPE" = "tcp" ] || { skip "NETTYPE != tcp" && return 0; }
1180         [ "$mds_HOST" = "`hostname`" ] || { skip "remote MDS" && return 0; }
1181         [ "$ost_HOST" = "`hostname`" -o "$ost1_HOST" = "`hostname`" ] || \
1182                 { skip "remote OST" && return 0; }
1183
1184         [ -z "$TUNEFS" ] && skip "No tunefs" && return
1185         local DISK1_4=$LUSTRE/tests/disk1_4.zip
1186         [ ! -r $DISK1_4 ] && skip "Cant find $DISK1_4, skipping" && return
1187
1188         local tmpdir=$TMP/conf32a
1189         unzip -o -j -d $tmpdir $DISK1_4 || { skip "Cant unzip $DISK1_4, skipping" && return ; }
1190         load_modules
1191         lctl set_param debug=$PTLDEBUG
1192
1193         $TUNEFS $tmpdir/mds || error "tunefs failed"
1194         # nids are wrong, so client wont work, but server should start
1195         start mds $tmpdir/mds "-o loop,exclude=lustre-OST0000" || return 3
1196         local UUID=$(lctl get_param -n mdt.lustre-MDT0000.uuid)
1197         echo MDS uuid $UUID
1198         [ "$UUID" == "mdsA_UUID" ] || error "UUID is wrong: $UUID" 
1199
1200         $TUNEFS --mgsnode=`hostname` $tmpdir/ost1 || error "tunefs failed"
1201         start ost1 $tmpdir/ost1 "-o loop" || return 5
1202         UUID=$(lctl get_param -n obdfilter.lustre-OST0000.uuid)
1203         echo OST uuid $UUID
1204         [ "$UUID" == "ost1_UUID" ] || error "UUID is wrong: $UUID" 
1205
1206         local NID=$($LCTL list_nids | head -1)
1207
1208         echo "OSC changes should return err:" 
1209         $LCTL conf_param lustre-OST0000.osc.max_dirty_mb=15 && return 7
1210         $LCTL conf_param lustre-OST0000.failover.node=$NID && return 8
1211         echo "ok."
1212         echo "MDC changes should succeed:" 
1213         $LCTL conf_param lustre-MDT0000.mdc.max_rpcs_in_flight=9 || return 9
1214         $LCTL conf_param lustre-MDT0000.failover.node=$NID || return 10
1215         echo "ok."
1216
1217         # With a new good MDT failover nid, we should be able to mount a client
1218         # (but it cant talk to OST)
1219         local OLDMOUNTOPT=$MOUNTOPT
1220         MOUNTOPT="exclude=lustre-OST0000"
1221         mount_client $MOUNT
1222         MOUNTOPT=$OLDMOUNTOPT
1223         set_and_check client "lctl get_param -n mdc.*.max_rpcs_in_flight" "lustre-MDT0000.mdc.max_rpcs_in_flight" ||
1224                 return 11
1225
1226         zconf_umount `hostname` $MOUNT -f
1227         cleanup_nocli
1228         load_modules
1229
1230         # mount a second time to make sure we didnt leave upgrade flag on
1231         load_modules
1232         $TUNEFS --dryrun $tmpdir/mds || error "tunefs failed"
1233         load_modules
1234         start mds $tmpdir/mds "-o loop,exclude=lustre-OST0000" || return 12
1235         cleanup_nocli
1236
1237         rm -rf $tmpdir || true  # true is only for TMP on NFS
1238 }
1239 run_test 32a "Upgrade from 1.4 (not live)"
1240
1241 test_32b() {
1242         # XXX - make this run on client-only systems with real hardware on
1243         #       the OST and MDT
1244         #       there appears to be a lot of assumption here about loopback
1245         #       devices
1246         # or maybe this test is just totally useless on a client-only system
1247         [ "$NETTYPE" = "tcp" ] || { skip "NETTYPE != tcp" && return 0; }
1248         [ "$mds_HOST" = "`hostname`" ] || { skip "remote MDS" && return 0; }
1249         [ "$ost_HOST" = "`hostname`" -o "$ost1_HOST" = "`hostname`" ] || \
1250                 { skip "remote OST" && return 0; }
1251
1252         [ -z "$TUNEFS" ] && skip "No tunefs" && return
1253         local DISK1_4=$LUSTRE/tests/disk1_4.zip
1254         [ ! -r $DISK1_4 ] && skip "Cant find $DISK1_4, skipping" && return
1255
1256         local tmpdir=$TMP/conf32b
1257         unzip -o -j -d $tmpdir $DISK1_4 || { skip "Cant unzip $DISK1_4, skipping" && return ; }
1258         load_modules
1259         lctl set_param debug=$PTLDEBUG
1260         NEWNAME=sofia
1261
1262         # writeconf will cause servers to register with their current nids
1263         $TUNEFS --writeconf --fsname=$NEWNAME $tmpdir/mds || error "tunefs failed"
1264         start mds $tmpdir/mds "-o loop" || return 3
1265         local UUID=$(lctl get_param -n mdt.${NEWNAME}-MDT0000.uuid)
1266         echo MDS uuid $UUID
1267         [ "$UUID" == "mdsA_UUID" ] || error "UUID is wrong: $UUID" 
1268
1269         $TUNEFS --mgsnode=`hostname` --fsname=$NEWNAME --writeconf $tmpdir/ost1 || error "tunefs failed"
1270         start ost1 $tmpdir/ost1 "-o loop" || return 5
1271         UUID=$(lctl get_param -n obdfilter.${NEWNAME}-OST0000.uuid)
1272         echo OST uuid $UUID
1273         [ "$UUID" == "ost1_UUID" ] || error "UUID is wrong: $UUID"
1274
1275         echo "OSC changes should succeed:" 
1276         $LCTL conf_param ${NEWNAME}-OST0000.osc.max_dirty_mb=15 || return 7
1277         $LCTL conf_param ${NEWNAME}-OST0000.failover.node=$NID || return 8
1278         echo "ok."
1279         echo "MDC changes should succeed:" 
1280         $LCTL conf_param ${NEWNAME}-MDT0000.mdc.max_rpcs_in_flight=9 || return 9
1281         echo "ok."
1282
1283         # MDT and OST should have registered with new nids, so we should have
1284         # a fully-functioning client
1285         echo "Check client and old fs contents"
1286         OLDFS=$FSNAME
1287         FSNAME=$NEWNAME
1288         mount_client $MOUNT
1289         FSNAME=$OLDFS
1290         set_and_check client "lctl get_param -n mdc.*.max_rpcs_in_flight" "${NEWNAME}-MDT0000.mdc.max_rpcs_in_flight" || return 11
1291         [ "$(cksum $MOUNT/passwd | cut -d' ' -f 1,2)" == "2479747619 779" ] || return 12  
1292         echo "ok."
1293
1294         cleanup
1295         rm -rf $tmpdir || true  # true is only for TMP on NFS
1296 }
1297 run_test 32b "Upgrade from 1.4 with writeconf"
1298
1299 test_33a() { # bug 12333, was test_33
1300         local rc=0
1301         local FSNAME2=test-123
1302         [ -n "$ost1_HOST" ] && fs2ost_HOST=$ost1_HOST
1303
1304         if [ -z "$fs2ost_DEV" -o -z "$fs2mds_DEV" ]; then
1305                 do_facet $SINGLEMDS [ -b "$MDSDEV" ] && \
1306                 skip "mixed loopback and real device not working" && return
1307         fi
1308
1309         local fs2mdsdev=${fs2mds_DEV:-${MDSDEV}_2}
1310         local fs2ostdev=${fs2ost_DEV:-$(ostdevname 1)_2}
1311         add fs2mds $MDS_MKFS_OPTS --fsname=${FSNAME2} --reformat $fs2mdsdev || exit 10
1312         add fs2ost $OST_MKFS_OPTS --fsname=${FSNAME2} --index=8191 --mgsnode=$MGSNID --reformat $fs2ostdev || exit 10
1313
1314         start fs2mds $fs2mdsdev $MDS_MOUNT_OPTS && trap cleanup_24a EXIT INT
1315         start fs2ost $fs2ostdev $OST_MOUNT_OPTS
1316         do_facet mds "$LCTL conf_param $FSNAME2.sys.timeout=200" || rc=1
1317         mkdir -p $MOUNT2
1318         mount -t lustre $MGSNID:/${FSNAME2} $MOUNT2 || rc=2
1319         echo "ok."
1320
1321         umount -d $MOUNT2
1322         stop fs2ost -f
1323         stop fs2mds -f
1324         rm -rf $MOUNT2 $fs2mdsdev $fs2ostdev
1325         cleanup_nocli || rc=6
1326         return $rc
1327 }
1328 run_test 33a "Mount ost with a large index number"
1329
1330 test_33b() {    # was test_34
1331         setup
1332
1333         do_facet client dd if=/dev/zero of=$MOUNT/24 bs=1024k count=1
1334         # Drop lock cancelation reply during umount
1335         #define OBD_FAIL_LDLM_CANCEL             0x304
1336         do_facet client lctl set_param fail_loc=0x80000304
1337         #lctl set_param debug=-1
1338         umount_client $MOUNT
1339         cleanup
1340 }
1341 run_test 33b "Drop cancel during umount"
1342
1343 test_34a() {
1344         setup
1345         do_facet client "sh runmultiop_bg_pause $DIR/file O_c"
1346         manual_umount_client
1347         rc=$?
1348         do_facet client killall -USR1 multiop
1349         if [ $rc -eq 0 ]; then
1350                 error "umount not fail!"
1351         fi
1352         sleep 1
1353         cleanup
1354 }
1355 run_test 34a "umount with opened file should be fail"
1356
1357
1358 test_34b() {
1359         setup
1360         touch $DIR/$tfile || return 1
1361         stop_mds --force || return 2
1362
1363         manual_umount_client --force
1364         rc=$?
1365         if [ $rc -ne 0 ]; then
1366                 error "mtab after failed umount - rc $rc"
1367         fi
1368
1369         cleanup
1370         return 0        
1371 }
1372 run_test 34b "force umount with failed mds should be normal"
1373
1374 test_34c() {
1375         setup
1376         touch $DIR/$tfile || return 1
1377         stop_ost --force || return 2
1378
1379         manual_umount_client --force
1380         rc=$?
1381         if [ $rc -ne 0 ]; then
1382                 error "mtab after failed umount - rc $rc"
1383         fi
1384
1385         cleanup
1386         return 0        
1387 }
1388 run_test 34c "force umount with failed ost should be normal"
1389
1390 test_35() { # bug 12459
1391         setup
1392
1393         DBG_SAVE="`lctl get_param -n debug`"
1394         lctl set_param debug="ha"
1395
1396         log "Set up a fake failnode for the MDS"
1397         FAKENID="127.0.0.2"
1398         do_facet mds $LCTL conf_param ${FSNAME}-MDT0000.failover.node=$FAKENID || return 4
1399
1400         log "Wait for RECONNECT_INTERVAL seconds (10s)"
1401         sleep 10
1402
1403         MSG="conf-sanity.sh test_35 `date +%F%kh%Mm%Ss`"
1404         $LCTL clear
1405         log "$MSG"
1406         log "Stopping the MDT:"
1407         stop_mds || return 5
1408
1409         df $MOUNT > /dev/null 2>&1 &
1410         DFPID=$!
1411         log "Restarting the MDT:"
1412         start_mds || return 6
1413         log "Wait for df ($DFPID) ... "
1414         wait $DFPID
1415         log "done"
1416         lctl set_param debug="$DBG_SAVE"
1417
1418         # retrieve from the log the first server that the client tried to
1419         # contact after the connection loss
1420         $LCTL dk $TMP/lustre-log-$TESTNAME.log
1421         NEXTCONN=`awk "/${MSG}/ {start = 1;}
1422                        /import_select_connection.*${FSNAME}-MDT0000-mdc.* using connection/ {
1423                                 if (start) {
1424                                         if (\\\$NF ~ /$FAKENID/)
1425                                                 print \\\$NF;
1426                                         else
1427                                                 print 0;
1428                                         exit;
1429                                 }
1430                        }" $TMP/lustre-log-$TESTNAME.log`
1431         [ "$NEXTCONN" != "0" ] && log "The client didn't try to reconnect to the last active server (tried ${NEXTCONN} instead)" && return 7
1432         cleanup
1433 }
1434 run_test 35 "Reconnect to the last active server first"
1435
1436 test_36() { # 12743
1437         local rc
1438         local FSNAME2=test1234
1439         local fs3ost_HOST=$ost_HOST
1440
1441         [ -n "$ost1_HOST" ] && fs2ost_HOST=$ost1_HOST && fs3ost_HOST=$ost1_HOST
1442         rc=0
1443
1444         if [ -z "$fs2ost_DEV" -o -z "$fs2mds_DEV" -o -z "$fs3ost_DEV" ]; then
1445                 do_facet $SINGLEMDS [ -b "$MDSDEV" ] && \
1446                 skip "mixed loopback and real device not working" && return
1447         fi
1448         [ $OSTCOUNT -lt 2 ] && skip "skipping test for single OST" && return
1449
1450         [ "$ost_HOST" = "`hostname`" -o "$ost1_HOST" = "`hostname`" ] || \
1451                 { skip "remote OST" && return 0; }
1452
1453         local fs2mdsdev=${fs2mds_DEV:-${MDSDEV}_2}
1454         local fs2ostdev=${fs2ost_DEV:-$(ostdevname 1)_2}
1455         local fs3ostdev=${fs3ost_DEV:-$(ostdevname 2)_2}
1456         add fs2mds $MDS_MKFS_OPTS --fsname=${FSNAME2} --reformat $fs2mdsdev || exit 10
1457         # XXX after we support non 4K disk blocksize, change following --mkfsoptions with
1458         # other argument
1459         add fs2ost $OST_MKFS_OPTS --mkfsoptions='-b4096' --fsname=${FSNAME2} --mgsnode=$MGSNID --reformat $fs2ostdev || exit 10
1460         add fs3ost $OST_MKFS_OPTS --mkfsoptions='-b4096' --fsname=${FSNAME2} --mgsnode=$MGSNID --reformat $fs3ostdev || exit 10
1461
1462         start fs2mds $fs2mdsdev $MDS_MOUNT_OPTS
1463         start fs2ost $fs2ostdev $OST_MOUNT_OPTS
1464         start fs3ost $fs3ostdev $OST_MOUNT_OPTS
1465         mkdir -p $MOUNT2
1466         mount -t lustre $MGSNID:/${FSNAME2} $MOUNT2 || return 1
1467
1468         sleep 5 # until 11778 fixed
1469
1470         dd if=/dev/zero of=$MOUNT2/$tfile bs=1M count=7 || return 2
1471
1472         BKTOTAL=`lctl get_param -n obdfilter.*.kbytestotal | awk 'BEGIN{total=0}; {total+=$1}; END{print total}'`
1473         BKFREE=`lctl get_param -n obdfilter.*.kbytesfree | awk 'BEGIN{free=0}; {free+=$1}; END{print free}'`
1474         BKAVAIL=`lctl get_param -n obdfilter.*.kbytesavail | awk 'BEGIN{avail=0}; {avail+=$1}; END{print avail}'`
1475         STRING=`df -P $MOUNT2 | tail -n 1 | awk '{print $2","$3","$4}'`
1476         DFTOTAL=`echo $STRING | cut -d, -f1`
1477         DFUSED=`echo $STRING  | cut -d, -f2`
1478         DFAVAIL=`echo $STRING | cut -d, -f3`
1479         DFFREE=$(($DFTOTAL - $DFUSED))
1480
1481         ALLOWANCE=$((64 * $OSTCOUNT))
1482
1483         if [ $DFTOTAL -lt $(($BKTOTAL - $ALLOWANCE)) ] ||  
1484            [ $DFTOTAL -gt $(($BKTOTAL + $ALLOWANCE)) ] ; then
1485                 echo "**** FAIL: df total($DFTOTAL) mismatch OST total($BKTOTAL)"
1486                 rc=1
1487         fi
1488         if [ $DFFREE -lt $(($BKFREE - $ALLOWANCE)) ] || 
1489            [ $DFFREE -gt $(($BKFREE + $ALLOWANCE)) ] ; then
1490                 echo "**** FAIL: df free($DFFREE) mismatch OST free($BKFREE)"
1491                 rc=2
1492         fi
1493         if [ $DFAVAIL -lt $(($BKAVAIL - $ALLOWANCE)) ] || 
1494            [ $DFAVAIL -gt $(($BKAVAIL + $ALLOWANCE)) ] ; then
1495                 echo "**** FAIL: df avail($DFAVAIL) mismatch OST avail($BKAVAIL)"
1496                 rc=3
1497        fi
1498
1499         umount -d $MOUNT2
1500         stop fs3ost -f || return 200
1501         stop fs2ost -f || return 201
1502         stop fs2mds -f || return 202
1503         rm -rf $MOUNT2 $fs2mdsdev $fs2ostdev $fs3ostdev
1504         unload_modules || return 203
1505         return $rc
1506 }
1507 run_test 36 "df report consistency on OSTs with different block size"
1508
1509 test_37() {
1510         [ -n "$CLIENTONLY" -o -n "$CLIENTMODSONLY" ] && skip "client only testing" && return 0
1511         LOCAL_MDSDEV="$TMP/mdt.img"
1512         SYM_MDSDEV="$TMP/sym_mdt.img"
1513
1514         echo "MDS :     $LOCAL_MDSDEV"
1515         echo "SYMLINK : $SYM_MDSDEV"
1516         rm -f $LOCAL_MDSDEV
1517
1518         touch $LOCAL_MDSDEV
1519         mkfs.lustre --reformat --fsname=lustre --mdt --mgs --device-size=9000 $LOCAL_MDSDEV ||
1520                 error "mkfs.lustre $LOCAL_MDSDEV failed"
1521         ln -s $LOCAL_MDSDEV $SYM_MDSDEV
1522
1523         echo "mount symlink device - $SYM_MDSDEV"
1524
1525         mount_op=`mount -v -t lustre -o loop $SYM_MDSDEV ${MOUNT%/*}/mds 2>&1 | grep "unable to set tunable"`
1526         umount -d ${MOUNT%/*}/mds
1527         rm -f $LOCAL_MDSDEV $SYM_MDSDEV
1528
1529         if [ -n "$mount_op" ]; then
1530                 error "**** FAIL: set tunables failed for symlink device"
1531         fi
1532         return 0
1533 }
1534 run_test 37 "verify set tunables works for symlink device"
1535
1536 test_38() { # bug 14222
1537         setup
1538         # like runtests
1539         COUNT=10
1540         SRC="/etc /bin"
1541         FILES=`find $SRC -type f -mtime +1 | head -n $COUNT`
1542         log "copying $(echo $FILES | wc -w) files to $DIR/$tdir"
1543         mkdir -p $DIR/$tdir
1544         tar cf - $FILES | tar xf - -C $DIR/$tdir || \
1545                 error "copying $SRC to $DIR/$tdir"
1546         sync
1547         umount_client $MOUNT
1548         stop_mds
1549         log "rename lov_objid file on MDS"
1550         rm -f $TMP/lov_objid.orig
1551         do_facet mds "debugfs -c -R \\\"dump lov_objid $TMP/lov_objid.orig\\\" $MDSDEV"
1552         do_facet mds "debugfs -w -R \\\"rm lov_objid\\\" $MDSDEV"
1553
1554         do_facet mds "od -Ax -td8 $TMP/lov_objid.orig"
1555         # check create in mds_lov_connect
1556         start_mds
1557         mount_client $MOUNT
1558         for f in $FILES; do
1559                 [ $V ] && log "verifying $DIR/$tdir/$f"
1560                 diff -q $f $DIR/$tdir/$f || ERROR=y
1561         done
1562         do_facet mds "debugfs -c -R \\\"dump lov_objid $TMP/lov_objid.new\\\"  $MDSDEV"
1563         do_facet mds "od -Ax -td8 $TMP/lov_objid.new"
1564         [ "$ERROR" = "y" ] && error "old and new files are different after connect" || true     
1565         
1566         # check it's updates in sync
1567         umount_client $MOUNT
1568         stop_mds
1569
1570         do_facet mds dd if=/dev/zero of=$TMP/lov_objid.clear bs=4096 count=1
1571         do_facet mds "debugfs -w -R \\\"rm lov_objid\\\" $MDSDEV"
1572         do_facet mds "debugfs -w -R \\\"write $TMP/lov_objid.clear lov_objid\\\" $MDSDEV "
1573
1574         start_mds
1575         mount_client $MOUNT
1576         for f in $FILES; do
1577                 [ $V ] && log "verifying $DIR/$tdir/$f"
1578                 diff -q $f $DIR/$tdir/$f || ERROR=y
1579         done
1580         do_facet mds "debugfs -c -R \\\"dump lov_objid $TMP/lov_objid.new1\\\" $MDSDEV"
1581         do_facet mds "od -Ax -td8 $TMP/lov_objid.new1"
1582         umount_client $MOUNT
1583         stop_mds
1584         [ "$ERROR" = "y" ] && error "old and new files are different after sync" || true
1585         
1586         log "files compared the same"
1587         cleanup
1588 }
1589 run_test 38 "MDS recreates missing lov_objid file from OST data"
1590
1591 test_39() {
1592         PTLDEBUG=+malloc
1593         setup
1594         cleanup
1595         perl $SRCDIR/leak_finder.pl $TMP/debug 2>&1 | egrep '*** Leak:' && 
1596                 error "memory leak detected" || true
1597 }
1598 run_test 39 "leak_finder recognizes both LUSTRE and LNET malloc messages"
1599
1600 test_40() { # bug 15759
1601         start_ost
1602         #define OBD_FAIL_TGT_TOOMANY_THREADS     0x706
1603         do_facet mds "sysctl -w lustre.fail_loc=0x80000706"
1604         start_mds
1605         cleanup
1606 }
1607 run_test 40 "race during service thread startup"
1608
1609 test_41() { #bug 14134
1610         local rc
1611         start mds $MDSDEV $MDS_MOUNT_OPTS -o nosvc -n
1612         start ost1 `ostdevname 1` $OST_MOUNT_OPTS
1613         start mds $MDSDEV $MDS_MOUNT_OPTS -o nomgs
1614         mkdir -p $MOUNT
1615         mount_client $MOUNT || return 1
1616         sleep 5
1617
1618         echo "blah blah" > $MOUNT/$tfile
1619         cat $MOUNT/$tfile
1620
1621         umount_client $MOUNT
1622         stop ost1 -f || return 201
1623         stop mds -f || return 202
1624         stop mds -f || return 203
1625         unload_modules || return 204
1626         return $rc
1627 }
1628 run_test 41 "mount mds with --nosvc and --nomgs"
1629
1630 test_42() { #bug 14693
1631         setup
1632         check_mount || return 2
1633         do_facet client lctl conf_param lustre.llite.some_wrong_param=10
1634         umount_client $MOUNT
1635         mount_client $MOUNT || return 1
1636         cleanup
1637         return 0
1638 }
1639 run_test 42 "invalid config param should not prevent client from mounting"
1640
1641 umount_client $MOUNT
1642 cleanup_nocli
1643 cleanup_gss
1644
1645 equals_msg `basename $0`: test complete
1646 [ -f "$TESTSUITELOG" ] && cat $TESTSUITELOG || true