xref: /titanic_52/usr/src/cmd/tail/tests/tailtests.sh (revision 72102e7461c97dc268d21d9dd8f02da45f174acd)
1209e49b2SChris Love#!/bin/bash
2209e49b2SChris Love#
3209e49b2SChris Love#
4209e49b2SChris Love# This file and its contents are supplied under the terms of the
5209e49b2SChris Love# Common Development and Distribution License ("CDDL"), version 1.0.
6209e49b2SChris Love# You may only use this file in accordance with the terms of version
7209e49b2SChris Love# 1.0 of the CDDL.
8209e49b2SChris Love#
9209e49b2SChris Love# A full copy of the text of the CDDL should have accompanied this
10209e49b2SChris Love# source.  A copy is of the CDDL is also available via the Internet
11209e49b2SChris Love# at http://www.illumos.org/license/CDDL.
12209e49b2SChris Love#
13209e49b2SChris Love
14209e49b2SChris Love#
15209e49b2SChris Love# Copyright 2010 Chris Love.  All rights reserved.
16*72102e74SBryan Cantrill# Copyright (c) 2013, Joyent, Inc. All rights reserved.
17209e49b2SChris Love#
18209e49b2SChris Love
19*72102e74SBryan Cantrillchecktest()
20*72102e74SBryan Cantrill{
21*72102e74SBryan Cantrill	local actual=$1
22*72102e74SBryan Cantrill	local output=$2
23*72102e74SBryan Cantrill	local test=$3
24*72102e74SBryan Cantrill
25*72102e74SBryan Cantrill	if [[ "$actual" != "$output" ]]; then
26*72102e74SBryan Cantrill		echo "$CMD: test $test: FAIL"
27*72102e74SBryan Cantrill		echo -e "$CMD: test $test: expected output:\n$output"
28*72102e74SBryan Cantrill		echo -e "$CMD: test $test: actual output:\n$actual"
29*72102e74SBryan Cantrill	else
30*72102e74SBryan Cantrill		echo "$CMD: test $test: pass"
31*72102e74SBryan Cantrill	fi
32*72102e74SBryan Cantrill}
33209e49b2SChris Love
34209e49b2SChris Love#
35209e49b2SChris Love# Test cases for 'tail', some based on CoreUtils test cases (validated
36*72102e74SBryan Cantrill# with legacy Solaris 'tail' and/or xpg4 'tail').  Note that this is designed
37*72102e74SBryan Cantrill# to be able to run on BSD systems as well to check our behavior against
38*72102e74SBryan Cantrill# theirs (some behavior that is known to be idiosyncratic to illumos is
39*72102e74SBryan Cantrill# skipped on non-illumos systems).
40209e49b2SChris Love#
41209e49b2SChris LovePROG=/usr/bin/tail
42*72102e74SBryan CantrillCMD=`basename $0`
43*72102e74SBryan CantrillDIR=""
44209e49b2SChris Love
45*72102e74SBryan Cantrillwhile [[ $# -gt 0 ]]; do
46209e49b2SChris Love	case $1 in
47209e49b2SChris Love	    -x)
48209e49b2SChris Love		PROG=/usr/xpg4/bin/tail
49*72102e74SBryan Cantrill		shift
50209e49b2SChris Love		;;
51209e49b2SChris Love	    -o)
52209e49b2SChris Love		PROG=$2
53*72102e74SBryan Cantrill		shift 2
54209e49b2SChris Love		;;
55*72102e74SBryan Cantrill	    -d)
56*72102e74SBryan Cantrill		DIR=$2
57*72102e74SBryan Cantrill		shift 2
58*72102e74SBryan Cantrill		;;
59*72102e74SBryan Cantrill	    *)
60*72102e74SBryan Cantrill		echo "Usage: tailtests.sh" \
61*72102e74SBryan Cantrill		    "[-x][-o <override tail executable>]" \
62*72102e74SBryan Cantrill		    "[-d <override output directory>]"
63209e49b2SChris Love		exit 1
64209e49b2SChris Love		;;
65209e49b2SChris Love	esac
66*72102e74SBryan Cantrilldone
67209e49b2SChris Love
68*72102e74SBryan Cantrill#
69*72102e74SBryan Cantrill# Shut bash up upon receiving a term so we can drop it on our children
70*72102e74SBryan Cantrill# without disrupting the output.
71*72102e74SBryan Cantrill#
72*72102e74SBryan Cantrilltrap "exit 0" TERM
73*72102e74SBryan Cantrill
74*72102e74SBryan Cantrillecho "$CMD: program is $PROG"
75*72102e74SBryan Cantrill
76*72102e74SBryan Cantrillif [[ $DIR != "" ]]; then
77*72102e74SBryan Cantrill	echo "$CMD: directory is $DIR"
78*72102e74SBryan Cantrillfi
79209e49b2SChris Love
80209e49b2SChris Loveo=`echo -e "bcd"`
81209e49b2SChris Lovea=`echo -e "abcd" | $PROG +2c`
82*72102e74SBryan Cantrillchecktest "$a" "$o" 1
83209e49b2SChris Love
84209e49b2SChris Loveo=`echo -e ""`
85209e49b2SChris Lovea=`echo "abcd" | $PROG +8c`
86*72102e74SBryan Cantrillchecktest "$a" "$o" 2
87209e49b2SChris Love
88209e49b2SChris Loveo=`echo -e "abcd"`
89209e49b2SChris Lovea=`echo "abcd" | $PROG -9c`
90*72102e74SBryan Cantrillchecktest "$a" "$o" 3
91209e49b2SChris Love
92209e49b2SChris Loveo=`echo -e "x"`
93209e49b2SChris Lovea=`echo -e "x" | $PROG -1l`
94*72102e74SBryan Cantrillchecktest "$a" "$o" 4
95209e49b2SChris Love
96209e49b2SChris Loveo=`echo -e "\n"`
97209e49b2SChris Lovea=`echo -e "x\ny\n" | $PROG -1l`
98*72102e74SBryan Cantrillchecktest "$a" "$o" 5
99209e49b2SChris Love
100209e49b2SChris Loveo=`echo -e "y\n"`
101209e49b2SChris Lovea=`echo -e "x\ny\n" | $PROG -2l`
102*72102e74SBryan Cantrillchecktest "$a" "$o" 6
103209e49b2SChris Love
104209e49b2SChris Loveo=`echo -e "y"`
105209e49b2SChris Lovea=`echo -e "x\ny" | $PROG -1l`
106*72102e74SBryan Cantrillchecktest "$a" "$o" 7
107209e49b2SChris Love
108209e49b2SChris Loveo=`echo -e "x\ny\n"`
109209e49b2SChris Lovea=`echo -e "x\ny\n" | $PROG +1l`
110*72102e74SBryan Cantrillchecktest "$a" "$o" 8
111209e49b2SChris Love
112209e49b2SChris Loveo=`echo -e "y\n"`
113209e49b2SChris Lovea=`echo -e "x\ny\n" | $PROG +2l`
114*72102e74SBryan Cantrillchecktest "$a" "$o" 9
115209e49b2SChris Love
116209e49b2SChris Loveo=`echo -e "x"`
117209e49b2SChris Lovea=`echo -e "x" | $PROG -1`
118*72102e74SBryan Cantrillchecktest "$a" "$o" 10
119209e49b2SChris Love
120209e49b2SChris Loveo=`echo -e "\n"`
121209e49b2SChris Lovea=`echo -e "x\ny\n" | $PROG -1`
122*72102e74SBryan Cantrillchecktest "$a" "$o" 11
123209e49b2SChris Love
124209e49b2SChris Loveo=`echo -e "y\n"`
125209e49b2SChris Lovea=`echo -e "x\ny\n" | $PROG -2`
126*72102e74SBryan Cantrillchecktest "$a" "$o" 12
127209e49b2SChris Love
128209e49b2SChris Loveo=`echo -e "y"`
129209e49b2SChris Lovea=`echo -e "x\ny" | $PROG -1`
130*72102e74SBryan Cantrillchecktest "$a" "$o" 13
131209e49b2SChris Love
132209e49b2SChris Loveo=`echo -e "x\ny\n"`
133209e49b2SChris Lovea=`echo -e "x\ny\n" | $PROG +1`
134*72102e74SBryan Cantrillchecktest "$a" "$o" 14
135209e49b2SChris Love
136209e49b2SChris Loveo=`echo -e "y\n"`
137209e49b2SChris Lovea=`echo -e "x\ny\n" | $PROG +2`
138*72102e74SBryan Cantrillchecktest "$a" "$o" 15
139209e49b2SChris Love
140209e49b2SChris Loveo=`echo -e "yyz"`
141209e49b2SChris Lovea=`echo -e "xyyyyyyyyyyz" | $PROG +10c`
142*72102e74SBryan Cantrillchecktest "$a" "$o" 16
143209e49b2SChris Love
144209e49b2SChris Loveo=`echo -e "y\ny\nz"`
145209e49b2SChris Lovea=`echo -e "x\ny\ny\ny\ny\ny\ny\ny\ny\ny\ny\nz" | $PROG +10l`
146*72102e74SBryan Cantrillchecktest "$a" "$o" 17
147*72102e74SBryan Cantrill
148*72102e74SBryan Cantrillo=`echo -e "y\ny\ny\ny\ny\ny\ny\ny\ny\nz"`
149*72102e74SBryan Cantrilla=`echo -e "x\ny\ny\ny\ny\ny\ny\ny\ny\ny\ny\nz" | $PROG -10l`
150*72102e74SBryan Cantrillchecktest "$a" "$o" 18
151*72102e74SBryan Cantrill
152*72102e74SBryan Cantrill#
153*72102e74SBryan Cantrill# For reasons that are presumably as accidental as they are ancient, legacy
154*72102e74SBryan Cantrill# (and closed) Solaris tail(1) allows +c, +l and -l to be aliases for +10c,
155*72102e74SBryan Cantrill# +10l and -10l, respectively.  If we are on SunOS, verify that this silly
156*72102e74SBryan Cantrill# behavior is functional.
157*72102e74SBryan Cantrill#
158*72102e74SBryan Cantrillif [[ `uname -s` == "SunOS" ]]; then
159*72102e74SBryan Cantrill	o=`echo -e "yyz"`
160*72102e74SBryan Cantrill	a=`echo -e "xyyyyyyyyyyz" | $PROG +c`
161*72102e74SBryan Cantrill	checktest "$a" "$o" 16a
162209e49b2SChris Love
163209e49b2SChris Love	o=`echo -e "y\ny\nz"`
164209e49b2SChris Love	a=`echo -e "x\ny\ny\ny\ny\ny\ny\ny\ny\ny\ny\nz" | $PROG +l`
165*72102e74SBryan Cantrill	checktest "$a" "$o" 17a
166209e49b2SChris Love
167209e49b2SChris Love	o=`echo -e "y\ny\ny\ny\ny\ny\ny\ny\ny\nz"`
168209e49b2SChris Love	a=`echo -e "x\ny\ny\ny\ny\ny\ny\ny\ny\ny\ny\nz" | $PROG -l`
169*72102e74SBryan Cantrill	checktest "$a" "$o" 18a
170*72102e74SBryan Cantrillfi
171209e49b2SChris Love
172209e49b2SChris Loveo=`echo -e "c\nb\na"`
173209e49b2SChris Lovea=`echo -e "a\nb\nc" | $PROG -r`
174*72102e74SBryan Cantrillchecktest "$a" "$o" 19
175209e49b2SChris Love
176*72102e74SBryan Cantrill#
177*72102e74SBryan Cantrill# Now we want to do a series of follow tests.
178*72102e74SBryan Cantrill#
179*72102e74SBryan Cantrillif [[ $DIR == "" ]]; then
180*72102e74SBryan Cantrill	export TMPDIR=/var/tmp
181*72102e74SBryan Cantrill	tdir=$(mktemp -d -t tailtest.XXXXXXXX || exit 1)
182*72102e74SBryan Cantrillelse
183*72102e74SBryan Cantrill	tdir=$(mktemp -d $DIR/tailtest.XXXXXXXX || exit 1)
184*72102e74SBryan Cantrillfi
185209e49b2SChris Love
186*72102e74SBryan Cantrillfollow=$tdir/follow
187*72102e74SBryan Cantrillmoved=$tdir/follow.moved
188*72102e74SBryan Cantrillout=$tdir/out
189209e49b2SChris Love
190*72102e74SBryan Cantrill#
191*72102e74SBryan Cantrill# First, verify that following works in its most basic sense.
192*72102e74SBryan Cantrill#
193*72102e74SBryan Cantrillecho -e "a\nb\nc" > $follow
194*72102e74SBryan Cantrill$PROG -f $follow > $out 2> /dev/null &
195*72102e74SBryan Cantrillchild=$!
196*72102e74SBryan Cantrillsleep 2
197*72102e74SBryan Cantrillecho -e "d\ne\nf" >> $follow
198*72102e74SBryan Cantrillsleep 1
199*72102e74SBryan Cantrillkill $child
200*72102e74SBryan Cantrillsleep 1
201209e49b2SChris Love
202*72102e74SBryan Cantrillo=`echo -e "a\nb\nc\nd\ne\nf\n"`
203*72102e74SBryan Cantrilla=`cat $out`
204*72102e74SBryan Cantrillchecktest "$a" "$o" 20
205*72102e74SBryan Cantrillrm $follow
206*72102e74SBryan Cantrill
207*72102e74SBryan Cantrill#
208*72102e74SBryan Cantrill# Now verify that following correctly follows the file being moved.
209*72102e74SBryan Cantrill#
210*72102e74SBryan Cantrillecho -e "a\nb\nc" > $follow
211*72102e74SBryan Cantrill$PROG -f $follow > $out 2> /dev/null &
212*72102e74SBryan Cantrillchild=$!
213*72102e74SBryan Cantrillsleep 2
214*72102e74SBryan Cantrillmv $follow $moved
215*72102e74SBryan Cantrill
216*72102e74SBryan Cantrillecho -e "d\ne\nf" >> $moved
217*72102e74SBryan Cantrillsleep 1
218*72102e74SBryan Cantrillkill $child
219*72102e74SBryan Cantrillsleep 1
220*72102e74SBryan Cantrill
221*72102e74SBryan Cantrillo=`echo -e "a\nb\nc\nd\ne\nf\n"`
222*72102e74SBryan Cantrilla=`cat $out`
223*72102e74SBryan Cantrillchecktest "$a" "$o" 21
224*72102e74SBryan Cantrillrm $moved
225*72102e74SBryan Cantrill
226*72102e74SBryan Cantrill#
227*72102e74SBryan Cantrill# And now truncation with the new offset being less than the old offset.
228*72102e74SBryan Cantrill#
229*72102e74SBryan Cantrillecho -e "a\nb\nc" > $follow
230*72102e74SBryan Cantrill$PROG -f $follow > $out 2> /dev/null &
231*72102e74SBryan Cantrillchild=$!
232*72102e74SBryan Cantrillsleep 2
233*72102e74SBryan Cantrillecho -e "d\ne\nf" >> $follow
234*72102e74SBryan Cantrillsleep 1
235*72102e74SBryan Cantrillecho -e "g\nh\ni" > $follow
236*72102e74SBryan Cantrillsleep 1
237*72102e74SBryan Cantrillkill $child
238*72102e74SBryan Cantrillsleep 1
239*72102e74SBryan Cantrill
240*72102e74SBryan Cantrillo=`echo -e "a\nb\nc\nd\ne\nf\ng\nh\ni\n"`
241*72102e74SBryan Cantrilla=`cat $out`
242*72102e74SBryan Cantrillchecktest "$a" "$o" 22
243*72102e74SBryan Cantrillrm $follow
244*72102e74SBryan Cantrill
245*72102e74SBryan Cantrill#
246*72102e74SBryan Cantrill# And truncation with the new offset being greater than the old offset.
247*72102e74SBryan Cantrill#
248*72102e74SBryan Cantrillecho -e "a\nb\nc" > $follow
249*72102e74SBryan Cantrillsleep 1
250*72102e74SBryan Cantrill$PROG -f $follow > $out 2> /dev/null &
251*72102e74SBryan Cantrillchild=$!
252*72102e74SBryan Cantrillsleep 2
253*72102e74SBryan Cantrillecho -e "d\ne\nf" >> $follow
254*72102e74SBryan Cantrillsleep 1
255*72102e74SBryan Cantrillecho -e "g\nh\ni\nj\nk\nl\nm\no\np\nq" > $follow
256*72102e74SBryan Cantrillsleep 1
257*72102e74SBryan Cantrillkill $child
258*72102e74SBryan Cantrillsleep 1
259*72102e74SBryan Cantrill
260*72102e74SBryan Cantrillo=`echo -e "a\nb\nc\nd\ne\nf\ng\nh\ni\nj\nk\nl\nm\no\np\nq"`
261*72102e74SBryan Cantrilla=`cat $out`
262*72102e74SBryan Cantrillchecktest "$a" "$o" 23
263*72102e74SBryan Cantrillrm $follow
264*72102e74SBryan Cantrill
265*72102e74SBryan Cantrill#
266*72102e74SBryan Cantrill# Verify that we can follow the moved file and correctly see a truncation.
267*72102e74SBryan Cantrill#
268*72102e74SBryan Cantrillecho -e "a\nb\nc" > $follow
269*72102e74SBryan Cantrill$PROG -f $follow > $out 2> /dev/null &
270*72102e74SBryan Cantrillchild=$!
271*72102e74SBryan Cantrillsleep 2
272*72102e74SBryan Cantrillmv $follow $moved
273*72102e74SBryan Cantrill
274*72102e74SBryan Cantrillecho -e "d\ne\nf" >> $moved
275*72102e74SBryan Cantrillsleep 1
276*72102e74SBryan Cantrillecho -e "g\nh\ni\nj\nk\nl\nm\no\np\nq" > $moved
277*72102e74SBryan Cantrillsleep 1
278*72102e74SBryan Cantrillkill $child
279*72102e74SBryan Cantrillsleep 1
280*72102e74SBryan Cantrill
281*72102e74SBryan Cantrillo=`echo -e "a\nb\nc\nd\ne\nf\ng\nh\ni\nj\nk\nl\nm\no\np\nq"`
282*72102e74SBryan Cantrilla=`cat $out`
283*72102e74SBryan Cantrillchecktest "$a" "$o" 24
284*72102e74SBryan Cantrillrm $moved
285*72102e74SBryan Cantrill
286*72102e74SBryan Cantrill#
287*72102e74SBryan Cantrill# Verify that capital-F follow properly deals with truncation
288*72102e74SBryan Cantrill#
289*72102e74SBryan Cantrillecho -e "a\nb\nc" > $follow
290*72102e74SBryan Cantrill$PROG -F $follow > $out 2> /dev/null &
291*72102e74SBryan Cantrillchild=$!
292*72102e74SBryan Cantrillsleep 2
293*72102e74SBryan Cantrillecho -e "d\ne\nf" >> $follow
294*72102e74SBryan Cantrillsleep 1
295*72102e74SBryan Cantrillecho -e "g\nh\ni" > $follow
296*72102e74SBryan Cantrillsleep 1
297*72102e74SBryan Cantrillkill $child
298*72102e74SBryan Cantrillsleep 1
299*72102e74SBryan Cantrill
300*72102e74SBryan Cantrillo=`echo -e "a\nb\nc\nd\ne\nf\ng\nh\ni\n"`
301*72102e74SBryan Cantrilla=`cat $out`
302*72102e74SBryan Cantrillchecktest "$a" "$o" 25
303*72102e74SBryan Cantrillrm $follow
304*72102e74SBryan Cantrill
305*72102e74SBryan Cantrill#
306*72102e74SBryan Cantrill# Verify that capital-F follow _won't_ follow the moved file and will
307*72102e74SBryan Cantrill# correctly deal with recreation of the original file.
308*72102e74SBryan Cantrill#
309*72102e74SBryan Cantrillecho -e "a\nb\nc" > $follow
310*72102e74SBryan Cantrill$PROG -F $follow > $out 2> /dev/null &
311*72102e74SBryan Cantrillchild=$!
312*72102e74SBryan Cantrillsleep 2
313*72102e74SBryan Cantrillmv $follow $moved
314*72102e74SBryan Cantrill
315*72102e74SBryan Cantrillecho -e "x\ny\nz" >> $moved
316*72102e74SBryan Cantrill
317*72102e74SBryan Cantrill#
318*72102e74SBryan Cantrill# At this point, tail is polling on stat'ing the missing file; we need to
319*72102e74SBryan Cantrill# be sure to sleep long enough after recreating it to know that it will pick
320*72102e74SBryan Cantrill# it up.
321*72102e74SBryan Cantrill#
322*72102e74SBryan Cantrillecho -e "d\ne\nf" > $follow
323*72102e74SBryan Cantrillsleep 5
324*72102e74SBryan Cantrillkill $child
325*72102e74SBryan Cantrillsleep 1
326*72102e74SBryan Cantrill
327*72102e74SBryan Cantrillo=`echo -e "a\nb\nc\nd\ne\nf\n"`
328*72102e74SBryan Cantrilla=`cat $out`
329*72102e74SBryan Cantrillchecktest "$a" "$o" 26
330*72102e74SBryan Cantrillrm $moved
331*72102e74SBryan Cantrill
332*72102e74SBryan Cantrill#
333*72102e74SBryan Cantrill# Verify that following two files works.
334*72102e74SBryan Cantrill#
335*72102e74SBryan Cantrillecho -e "one" > $follow
336*72102e74SBryan Cantrillecho -e "two" > $moved
337*72102e74SBryan Cantrill$PROG -f $follow $moved > $out 2> /dev/null &
338*72102e74SBryan Cantrillchild=$!
339*72102e74SBryan Cantrillsleep 2
340*72102e74SBryan Cantrillecho -e "three" >> $follow
341*72102e74SBryan Cantrillsleep 1
342*72102e74SBryan Cantrillecho -e "four" >> $moved
343*72102e74SBryan Cantrillsleep 1
344*72102e74SBryan Cantrillecho -e "five" >> $follow
345*72102e74SBryan Cantrillsleep 1
346*72102e74SBryan Cantrillkill $child
347*72102e74SBryan Cantrillsleep 1
348*72102e74SBryan Cantrill
349*72102e74SBryan Cantrill# There is a bug where the content comes before the header lines,
350*72102e74SBryan Cantrill# where rlines/mapprint happens before the header.  A pain to fix.
351*72102e74SBryan Cantrill# In this test, just make sure we see both files change.
352*72102e74SBryan Cantrillo="one
353*72102e74SBryan Cantrill
354*72102e74SBryan Cantrill==> $follow <==
355*72102e74SBryan Cantrilltwo
356*72102e74SBryan Cantrill
357*72102e74SBryan Cantrill==> $moved <==
358*72102e74SBryan Cantrill
359*72102e74SBryan Cantrill==> $follow <==
360*72102e74SBryan Cantrillthree
361*72102e74SBryan Cantrill
362*72102e74SBryan Cantrill==> $moved <==
363*72102e74SBryan Cantrillfour
364*72102e74SBryan Cantrill
365*72102e74SBryan Cantrill==> $follow <==
366*72102e74SBryan Cantrillfive"
367*72102e74SBryan Cantrilla=`cat $out`
368*72102e74SBryan Cantrillchecktest "$a" "$o" 27
369*72102e74SBryan Cantrillrm $follow $moved
370*72102e74SBryan Cantrill
371*72102e74SBryan Cantrillif [[ `uname -s` == "SunOS" ]]; then
372*72102e74SBryan Cantrill	#
373*72102e74SBryan Cantrill	# Use DTrace to truncate the file between the return from port_get()
374*72102e74SBryan Cantrill	# and the reassociation of the file object with the port, exposing
375*72102e74SBryan Cantrill	# any race conditions whereby FILE_TRUNC events are lost.
376*72102e74SBryan Cantrill	#
377*72102e74SBryan Cantrill	cat /dev/null > $follow
378*72102e74SBryan Cantrill	dtrace -c "$PROG -f $follow" -s /dev/stdin > $out <<EOF
379*72102e74SBryan Cantrill		#pragma D option destructive
380*72102e74SBryan Cantrill		#pragma D option quiet 
381*72102e74SBryan Cantrill
382*72102e74SBryan Cantrill		pid\$target::port_get:return
383*72102e74SBryan Cantrill		/++i == 5/
384*72102e74SBryan Cantrill		{
385*72102e74SBryan Cantrill			stop();
386*72102e74SBryan Cantrill			system("cat /dev/null > $follow");
387*72102e74SBryan Cantrill			system("prun %d", pid);
388*72102e74SBryan Cantrill		}
389*72102e74SBryan Cantrill
390*72102e74SBryan Cantrill		tick-1sec
391*72102e74SBryan Cantrill		{
392*72102e74SBryan Cantrill			system("echo %d >> $follow", j++);
393*72102e74SBryan Cantrill		}
394*72102e74SBryan Cantrill
395*72102e74SBryan Cantrill		tick-1sec
396*72102e74SBryan Cantrill		/j == 10/
397*72102e74SBryan Cantrill		{
398*72102e74SBryan Cantrill			exit(0);
399*72102e74SBryan Cantrill		}
400*72102e74SBryan CantrillEOF
401*72102e74SBryan Cantrill
402*72102e74SBryan Cantrill	o=`echo -e "0\n1\n2\n3\n5\n6\n7\n8\n9\n"`
403*72102e74SBryan Cantrill	a=`cat $out`
404*72102e74SBryan Cantrill	checktest "$a" "$o" 27a
405*72102e74SBryan Cantrill	rm $follow
406*72102e74SBryan Cantrill
407*72102e74SBryan Cantrill	cat /dev/null > $follow
408*72102e74SBryan Cantrill	dtrace -c "$PROG -f $follow" -s /dev/stdin > $out <<EOF
409*72102e74SBryan Cantrill		#pragma D option destructive
410*72102e74SBryan Cantrill		#pragma D option quiet 
411*72102e74SBryan Cantrill
412*72102e74SBryan Cantrill		pid\$target::port_get:return
413*72102e74SBryan Cantrill		/++i == 5/
414*72102e74SBryan Cantrill		{
415*72102e74SBryan Cantrill			stop();
416*72102e74SBryan Cantrill			system("mv $follow $moved");
417*72102e74SBryan Cantrill			system("cat /dev/null > $moved");
418*72102e74SBryan Cantrill			system("prun %d", pid);
419*72102e74SBryan Cantrill		}
420*72102e74SBryan Cantrill
421*72102e74SBryan Cantrill		tick-1sec
422*72102e74SBryan Cantrill		{
423*72102e74SBryan Cantrill			system("echo %d >> %s", j++,
424*72102e74SBryan Cantrill			    i < 5 ? "$follow" : "$moved");
425*72102e74SBryan Cantrill		}
426*72102e74SBryan Cantrill
427*72102e74SBryan Cantrill		tick-1sec
428*72102e74SBryan Cantrill		/j == 10/
429*72102e74SBryan Cantrill		{
430*72102e74SBryan Cantrill			exit(0);
431*72102e74SBryan Cantrill		}
432*72102e74SBryan CantrillEOF
433*72102e74SBryan Cantrill
434*72102e74SBryan Cantrill	o=`echo -e "0\n1\n2\n3\n5\n6\n7\n8\n9\n"`
435*72102e74SBryan Cantrill	a=`cat $out`
436*72102e74SBryan Cantrill	checktest "$a" "$o" 27b
437*72102e74SBryan Cantrill	rm $moved
438*72102e74SBryan Cantrill
439*72102e74SBryan Cantrill	#
440*72102e74SBryan Cantrill	# Verify that -F will deal properly with the file being truncated
441*72102e74SBryan Cantrill	# not by truncation, but rather via an ftruncate() from logadm.
442*72102e74SBryan Cantrill	#
443*72102e74SBryan Cantrill	cat /dev/null > $follow
444*72102e74SBryan Cantrill	( $PROG -F $follow > $out ) &
445*72102e74SBryan Cantrill	child=$!
446*72102e74SBryan Cantrill	echo -e "a\nb\nc\nd\ne\nf" >> $follow
447*72102e74SBryan Cantrill	logadm -c $follow
448*72102e74SBryan Cantrill	sleep 2
449*72102e74SBryan Cantrill	echo -e "g\nh\ni" >> $follow
450*72102e74SBryan Cantrill	sleep 2
451*72102e74SBryan Cantrill	kill $child
452*72102e74SBryan Cantrill	sleep 1
453*72102e74SBryan Cantrill
454*72102e74SBryan Cantrill	o=`echo -e "a\nb\nc\nd\ne\nf\ng\nh\ni\n"`
455*72102e74SBryan Cantrill	a=`cat $out`
456*72102e74SBryan Cantrill	checktest "$a" "$o" 27c
457*72102e74SBryan Cantrillfi
458*72102e74SBryan Cantrill
459*72102e74SBryan Cantrill#
460*72102e74SBryan Cantrill# We're now going to test that while we may miss output due to truncations
461*72102e74SBryan Cantrill# occurring faster than tail can read, we don't ever repeat output.
462*72102e74SBryan Cantrill#
463*72102e74SBryan Cantrillcat /dev/null > $follow
464*72102e74SBryan Cantrill( $PROG -f $follow > $out ) &
465*72102e74SBryan Cantrilltchild=$!
466*72102e74SBryan Cantrill( let i=0 ; while true; do echo $i > $follow ; sleep 0.1; let i=i+1 ; done ) &
467*72102e74SBryan Cantrillchild=$!
468*72102e74SBryan Cantrillsleep 10
469*72102e74SBryan Cantrillkill $tchild
470*72102e74SBryan Cantrillkill $child
471*72102e74SBryan Cantrill
472*72102e74SBryan Cantrilla=`sort $out | uniq -c | sort -n | tail -1 | awk '{ print $1 }'`
473*72102e74SBryan Cantrillo=1
474*72102e74SBryan Cantrill
475*72102e74SBryan Cantrillchecktest "$a" "$o" 28
476*72102e74SBryan Cantrill
477*72102e74SBryan Cantrillecho "$CMD: completed"
478*72102e74SBryan Cantrill
479*72102e74SBryan Cantrillexit $errs
480*72102e74SBryan Cantrill
481