xref: /dragonfly/usr.sbin/crashinfo/crashinfo.sh (revision b58087dc)
1#!/bin/sh
2#
3# Copyright (c) 2008 Yahoo!, Inc.
4# All rights reserved.
5#
6# Redistribution and use in source and binary forms, with or without
7# modification, are permitted provided that the following conditions
8# are met:
9# 1. Redistributions of source code must retain the above copyright
10#    notice, this list of conditions and the following disclaimer.
11# 2. Redistributions in binary form must reproduce the above copyright
12#    notice, this list of conditions and the following disclaimer in the
13#    documentation and/or other materials provided with the distribution.
14# 3. Neither the name of the author nor the names of any co-contributors
15#    may be used to endorse or promote products derived from this software
16#    without specific prior written permission.
17#
18# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
19# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
21# ARE DISCLAIMED.  IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
22# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
23# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
24# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
25# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
26# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
27# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
28# SUCH DAMAGE.
29#
30# $FreeBSD$
31
32usage()
33{
34	echo "usage: crashinfo [-d crashdir] [-n dumpnr] [-k kernel] [core]"
35	exit 1
36}
37
38find_kernel()
39{
40	local ivers k kvers file
41
42	ivers=$(awk '
43	/Version String/ {
44		print
45		nextline=1
46		next
47	}
48	// {
49		if (nextline) {
50			print
51			nextline=0
52		}
53	}' $INFO)
54
55	file=`mktemp /tmp/crashinfo.XXXXXX`
56	if [ $? -eq 0 ]; then
57		echo 'printf "  Version String: %s", version' > $file
58		# Look for a matching kernel version.
59		for k in /boot/kernel/kernel $(ls -t $CRASHDIR/kern.*) $(ls -t /boot/*/kernel); do
60			kvers=$(gdb -x $file -batch $k 2>/dev/null)
61			if [ "$ivers" = "$kvers" ]; then
62				KERNEL=$k
63				KVERS=$kvers
64				break
65			fi
66		done
67		rm -f $file
68	fi
69}
70
71CRASHDIR=/var/crash
72DUMPNR=
73KERNEL=
74KVERS=
75
76while getopts "d:n:k:" opt; do
77	case "$opt" in
78	d)
79		CRASHDIR=$OPTARG
80		;;
81	n)
82		DUMPNR=$OPTARG
83		;;
84	k)
85		KERNEL=$OPTARG
86		;;
87	\?)
88		usage
89		;;
90	esac
91done
92
93shift $((OPTIND - 1))
94
95if [ $# -eq 1 ]; then
96	if [ -n "$DUMPNR" ]; then
97		echo "-n and an explicit vmcore are mutually exclusive"
98		usage
99	fi
100
101	# Figure out the crash directory and number from the vmcore name.
102	CRASHDIR=`dirname $1`
103	DUMPNR=$(expr $(basename $1) : 'vmcore\.\([0-9]*\)$')
104	if [ -z "$DUMPNR" ]; then
105		echo "Unable to determine dump number from vmcore file $1."
106		exit 1
107	fi
108elif [ $# -gt 1 ]; then
109	usage
110else
111	# If we don't have an explicit dump number, operate on the most
112	# recent dump.
113	if [ -z "$DUMPNR" ]; then
114		if ! [ -r $CRASHDIR/bounds ]; then
115			echo "No crash dumps in $CRASHDIR."
116			exit 1
117		fi
118		next=`cat $CRASHDIR/bounds`
119		if [ -z "$next" ] || [ "$next" -eq 0 ]; then
120			echo "No crash dumps in $CRASHDIR."
121			exit 1
122		fi
123		DUMPNR=$(($next - 1))
124	fi
125fi
126
127VMCORE=$CRASHDIR/vmcore.$DUMPNR
128INFO=$CRASHDIR/info.$DUMPNR
129FILE=$CRASHDIR/core.txt.$DUMPNR
130HOSTNAME=`hostname`
131
132if [ ! -e $VMCORE ]; then
133	echo "$VMCORE not found"
134	exit 1
135fi
136
137if [ ! -e $INFO ]; then
138	echo "$INFO not found"
139	exit 1
140fi
141
142# If the user didn't specify a kernel, then try to find one.
143if [ -z "$KERNEL" ]; then
144	find_kernel
145	if [ -z "$KERNEL" ]; then
146		echo "Unable to find matching kernel for $VMCORE"
147		exit 1
148	fi
149elif [ ! -e $KERNEL ]; then
150	echo "$KERNEL not found"
151	exit 1
152fi
153
154echo "Writing crash summary to $FILE."
155
156# Simulate uname
157#ostype=$(echo -e printf '"%s", ostype' | gdb -x /dev/stdin -batch $KERNEL)
158#osrelease=$(echo -e printf '"%s", osrelease' | gdb -x /dev/stdin -batch $KERNEL)
159#version=$(echo -e printf '"%s", version' | gdb -x /dev/stdin -batch $KERNEL | \
160#    tr '\t\n' '  ')
161#machine=$(echo -e printf '"%s", machine' | gdb -x /dev/stdin -batch $KERNEL)
162
163exec > $FILE 2>&1
164
165echo "$HOSTNAME dumped core - see $VMCORE"
166echo
167date
168echo
169#echo "$ostype $HOSTNAME $osrelease $version $machine"
170echo $KVERS
171echo
172sed -ne '/^  Panic String: /{s//panic: /;p;}' $INFO
173echo
174
175# XXX: /bin/sh on 7.0+ is broken so we can't simply pipe the commands to
176# kgdb via stdin and have to use a temporary file instead.
177file=`mktemp /tmp/crashinfo.XXXXXX`
178if [ $? -eq 0 ]; then
179	echo "bt" >> $file
180	if [ -e /usr/src/test/debug/gdb.kernel ]; then
181		echo "source /usr/src/test/debug/gdb.kernel" >> $file
182		echo "lstok" >> $file
183		echo "psx" >> $file
184		echo "running_threads" >> $file
185		echo "lsvfs" >> $file
186		echo "lsvfsops" >> $file
187		echo "lsmount" >> $file
188		echo "kldstat" >> $file
189	fi
190	echo "quit" >> $file
191	( ulimit -t 15; kgdb $KERNEL $VMCORE < $file )
192	rm -f $file
193	echo
194fi
195echo
196
197echo "------------------------------------------------------------------------"
198echo "ps -axl"
199echo
200ps -M $VMCORE -N $KERNEL -axl
201echo
202
203echo "------------------------------------------------------------------------"
204echo "vmstat -s"
205echo
206vmstat -M $VMCORE -N $KERNEL -s
207echo
208
209echo "------------------------------------------------------------------------"
210echo "vmstat -m"
211echo
212vmstat -M $VMCORE -N $KERNEL -m
213echo
214
215echo "------------------------------------------------------------------------"
216echo "vmstat -z"
217echo
218vmstat -M $VMCORE -N $KERNEL -z
219echo
220
221echo "------------------------------------------------------------------------"
222echo "vmstat -i"
223echo
224vmstat -M $VMCORE -N $KERNEL -i
225echo
226
227echo "------------------------------------------------------------------------"
228echo "pstat -T"
229echo
230pstat -M $VMCORE -N $KERNEL -T
231echo
232
233echo "------------------------------------------------------------------------"
234echo "pstat -s"
235echo
236pstat -M $VMCORE -N $KERNEL -s
237echo
238
239#echo "------------------------------------------------------------------------"
240#echo "iostat"
241#echo
242#iostat -M $VMCORE -N $KERNEL
243#echo
244
245echo "------------------------------------------------------------------------"
246echo "ipcs -a"
247echo
248ipcs -C $VMCORE -N $KERNEL -a
249echo
250
251echo "------------------------------------------------------------------------"
252echo "ipcs -T"
253echo
254ipcs -C $VMCORE -N $KERNEL -T
255echo
256
257# XXX: This doesn't actually work in 5.x+
258if false; then
259echo "------------------------------------------------------------------------"
260echo "w -dn"
261echo
262w -M $VMCORE -N $KERNEL -dn
263echo
264fi
265
266echo "------------------------------------------------------------------------"
267echo "nfsstat"
268echo
269nfsstat -M $VMCORE -N $KERNEL
270echo
271
272echo "------------------------------------------------------------------------"
273echo "netstat -s"
274echo
275netstat -M $VMCORE -N $KERNEL -s
276echo
277
278echo "------------------------------------------------------------------------"
279echo "netstat -m"
280echo
281netstat -M $VMCORE -N $KERNEL -m
282echo
283
284echo "------------------------------------------------------------------------"
285echo "netstat -id"
286echo
287netstat -M $VMCORE -N $KERNEL -id
288echo
289
290echo "------------------------------------------------------------------------"
291echo "netstat -anr"
292echo
293netstat -M $VMCORE -N $KERNEL -anr
294echo
295
296echo "------------------------------------------------------------------------"
297echo "netstat -anA"
298echo
299netstat -M $VMCORE -N $KERNEL -anA
300echo
301
302echo "------------------------------------------------------------------------"
303echo "netstat -aL"
304echo
305netstat -M $VMCORE -N $KERNEL -aL
306echo
307
308echo "------------------------------------------------------------------------"
309echo "fstat"
310echo
311fstat -M $VMCORE -N $KERNEL
312echo
313
314echo "------------------------------------------------------------------------"
315echo "dmesg"
316echo
317dmesg -a -M $VMCORE -N $KERNEL
318echo
319
320#echo "------------------------------------------------------------------------"
321#echo "kernel config"
322#echo
323#config -x $KERNEL
324