forked from Imagelibrary/binutils-gdb
With commit fb2ded33c1, I added
Fedora's gstack script to gdb. Some issues have arisen since
then, and this patch addresses those issues:
. As Sam James recently noted[1], PKGVERSION and VERSION
need to be quoted.
. A Fedora user reported the misuse of --readnever, which
causes gstack to omit filename and line number information in the
backtrace[Red Hat BZ 2354997].
[1] https://inbox.sourceware.org/gdb-patches/d19d6bc17e0a160ce27fc572079f11a587c0e168.1742424869.git.sam@gentoo.org/
Bug: https://bugzilla.redhat.com/show_bug.cgi?id=2354997
Bug: https://sourceware.org/bugzilla/show_bug.cgi?id=32828
148 lines
3.0 KiB
Bash
Executable File
148 lines
3.0 KiB
Bash
Executable File
#!/usr/bin/env bash
|
|
|
|
# Copyright (C) 2024-2025 Free Software Foundation, Inc.
|
|
|
|
# This program is free software; you can redistribute it and/or modify
|
|
# it under the terms of the GNU General Public License as published by
|
|
# the Free Software Foundation; either version 3 of the License, or
|
|
# (at your option) any later version.
|
|
#
|
|
# This program is distributed in the hope that it will be useful,
|
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
# GNU General Public License for more details.
|
|
#
|
|
# You should have received a copy of the GNU General Public License
|
|
# along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
# Print a stack trace of a running process.
|
|
# Similar to the gcore command, but instead of creating a core file,
|
|
# we simply have gdb print out the stack backtrace to the terminal.
|
|
|
|
GDB=${GDB:-$(command -v gdb)}
|
|
GDBARGS=${GDBARGS:-}
|
|
AWK=${AWK:-}
|
|
PKGVERSION="@PKGVERSION@"
|
|
VERSION="@VERSION@"
|
|
|
|
# Find an appropriate awk interpreter if one was not specified
|
|
# via the environment.
|
|
awk_prog=""
|
|
if [ -z "$AWK" ]; then
|
|
for prog in gawk mawk nawk awk; do
|
|
awk_prog=$(command -v $prog)
|
|
test -n "$awk_prog" && break
|
|
done
|
|
AWK="$awk_prog"
|
|
fi
|
|
if [ ! -x "$AWK" ]; then
|
|
echo "$0: could not find usable awk interpreter" 1>&2
|
|
exit 2
|
|
fi
|
|
|
|
function print_usage() {
|
|
echo "Usage: $0 [-h|--help] [-v|--version] PID"
|
|
}
|
|
|
|
function print_try_help() {
|
|
echo "Try '$0 --help' for more information."
|
|
}
|
|
|
|
function print_help() {
|
|
print_usage
|
|
echo "Print a stack trace of a running program"
|
|
echo
|
|
echo " -h, --help Print this message then exit."
|
|
echo " -v, --version Print version information then exit."
|
|
}
|
|
|
|
function print_version() {
|
|
echo "GNU gstack (${PKGVERSION}) ${VERSION}"
|
|
}
|
|
|
|
# Parse options.
|
|
while getopts hv-: OPT; do
|
|
if [ "$OPT" = "-" ]; then
|
|
OPT="${OPTARG%%=*}"
|
|
OPTARG="${OPTARG#'$OPT'}"
|
|
OPTARG="${OPTARG#=}"
|
|
fi
|
|
|
|
case "$OPT" in
|
|
h | help)
|
|
print_help
|
|
exit 0
|
|
;;
|
|
v | version)
|
|
print_version
|
|
exit 0
|
|
;;
|
|
\?)
|
|
# getopts has already output an error message.
|
|
print_try_help 1>&2
|
|
exit 2 ;;
|
|
*)
|
|
echo "$0: unrecognized option '--$OPT'" 1>&2
|
|
print_try_help 1>&2
|
|
exit 2
|
|
;;
|
|
esac
|
|
done
|
|
shift $((OPTIND-1))
|
|
|
|
# The sole remaining argument should be the PID of the process
|
|
# whose backtrace is desired.
|
|
if [ $# -ne 1 ]; then
|
|
print_usage 1>&2
|
|
exit 1
|
|
fi
|
|
|
|
PID=$1
|
|
|
|
awk_script=$(cat << EOF
|
|
BEGIN {
|
|
first=1
|
|
attach_okay=0
|
|
}
|
|
|
|
/ATTACHED/ {
|
|
attach_okay=1
|
|
}
|
|
|
|
/^#/ {
|
|
if (attach_okay) {
|
|
print \$0
|
|
}
|
|
}
|
|
|
|
/^Thread/ {
|
|
if (attach_okay) {
|
|
if (first == 0)
|
|
print ""
|
|
first=0
|
|
print \$0
|
|
}
|
|
}
|
|
|
|
END {
|
|
if (attach_okay == 0)
|
|
exit 2
|
|
}
|
|
EOF
|
|
)
|
|
|
|
# Run GDB and remove some unwanted noise.
|
|
"$GDB" --quiet -nx $GDBARGS <<EOF |
|
|
set width 0
|
|
set height 0
|
|
set pagination no
|
|
set debuginfod enabled off
|
|
define attach-bt
|
|
attach \$arg0
|
|
echo "ATTACHED"
|
|
thread apply all bt
|
|
end
|
|
attach-bt $PID
|
|
EOF
|
|
$AWK -- "$awk_script"
|