import gcc-toolset-10-gdb-9.2-4.el8
This commit is contained in:
parent
864c0e48ca
commit
b4ded77d97
@ -412,3 +412,79 @@ Patch101: gdb-rhbz1844458-use-fputX_unfiltered.patch
|
||||
# (Aaron Merey, RH BZ 183877)
|
||||
Patch102: gdb-rhbz1838777-debuginfod.patch
|
||||
|
||||
# Use pkg-config for debuginfod.m4.
|
||||
# (Aaron Merey)
|
||||
Patch103: debuginfod-use-pkg-config.patch
|
||||
|
||||
# Remove hack for GDB which sets the section size to 0
|
||||
# Kevin Buettner, RH BZ 1842691
|
||||
Patch104: gdb-rhbz1842691-corefile-mem-access-1of15.patch
|
||||
|
||||
# Adjust corefile.exp test to show regression after bfd hack removal
|
||||
# Kevin Buettner, RH BZ 1842691
|
||||
Patch105: gdb-rhbz1842691-corefile-mem-access-2of15.patch
|
||||
|
||||
# section_table_xfer_memory: Replace section name with callback predicate
|
||||
# Kevin Buettner, RH BZ 1842691
|
||||
Patch106: gdb-rhbz1842691-corefile-mem-access-3of15.patch
|
||||
|
||||
# Provide access to non SEC_HAS_CONTENTS core file sections
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch107: gdb-rhbz1842691-corefile-mem-access-4of15.patch
|
||||
|
||||
# Test ability to access unwritten-to mmap data in core file
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch108: gdb-rhbz1842691-corefile-mem-access-5of15.patch
|
||||
|
||||
# Update binary_get_section_contents to seek using section's file position
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch109: gdb-rhbz1842691-corefile-mem-access-6of15.patch
|
||||
|
||||
# Add new gdbarch method, read_core_file_mappings
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch110: gdb-rhbz1842691-corefile-mem-access-7of15.patch
|
||||
|
||||
# Use NT_FILE note section for reading core target memory
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch111: gdb-rhbz1842691-corefile-mem-access-8of15.patch
|
||||
|
||||
# Add test for accessing read-only mmapped data in a core file
|
||||
# Kevin Buettner, RH BZ 1842691
|
||||
Patch112: gdb-rhbz1842691-corefile-mem-access-9of15.patch
|
||||
|
||||
# gcore command: Place all file-backed mappings in NT_FILE note
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch113: gdb-rhbz1842691-corefile-mem-access-10of15.patch
|
||||
|
||||
# Adjust coredump-filter.exp to account for NT_FILE note handling
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch114: gdb-rhbz1842691-corefile-mem-access-11of15.patch
|
||||
|
||||
# Add new command "maint print core-file-backed-mappings"
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch115: gdb-rhbz1842691-corefile-mem-access-12of15.patch
|
||||
|
||||
# Add documentation for "maint print core-file-backed-mappings"
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch116: gdb-rhbz1842691-corefile-mem-access-13of15.patch
|
||||
|
||||
# New core file tests with mappings over existing program memory
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch117: gdb-rhbz1842691-corefile-mem-access-14of15.patch
|
||||
|
||||
# Add period to help text for maint print core-file-backed-mappings
|
||||
# Kevin Buettner, RH BZ 1842961
|
||||
Patch118: gdb-rhbz1842691-corefile-mem-access-15of15.patch
|
||||
|
||||
# Backport of "Exclude debuginfo files from 'outside of ELF segments'
|
||||
# warning" (Keith Seitz)
|
||||
Patch119: gdb-rhbz1898252-loadable-section-outside-ELF-segments.patch
|
||||
|
||||
# Backport "fortran dynamic type related fixes"
|
||||
# Andrew Burgess (RH BZ 1905702)
|
||||
Patch120: gdb-rhbz1905702-DWARF-data_location.patch
|
||||
|
||||
# Backport of "Correct recording of 'store on condition' insns"
|
||||
# Andreas Arnaz (RH BZ 1903374)
|
||||
Patch121: gdb-rhbz1903375-s390x-store-on-condition.patch
|
||||
|
||||
|
@ -100,3 +100,22 @@
|
||||
%patch100 -p1
|
||||
%patch101 -p1
|
||||
%patch102 -p1
|
||||
%patch103 -p1
|
||||
%patch104 -p1
|
||||
%patch105 -p1
|
||||
%patch106 -p1
|
||||
%patch107 -p1
|
||||
%patch108 -p1
|
||||
%patch109 -p1
|
||||
%patch110 -p1
|
||||
%patch111 -p1
|
||||
%patch112 -p1
|
||||
%patch113 -p1
|
||||
%patch114 -p1
|
||||
%patch115 -p1
|
||||
%patch116 -p1
|
||||
%patch117 -p1
|
||||
%patch118 -p1
|
||||
%patch119 -p1
|
||||
%patch120 -p1
|
||||
%patch121 -p1
|
||||
|
814
SOURCES/debuginfod-use-pkg-config.patch
Normal file
814
SOURCES/debuginfod-use-pkg-config.patch
Normal file
@ -0,0 +1,814 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Fri, 24 Jul 2020 16:09:15 -0400
|
||||
Subject: debuginfod-use-pkg-config.patch
|
||||
|
||||
;; Use pkg-config for debuginfod.m4.
|
||||
;; (Aaron Merey)
|
||||
|
||||
From: Aaron Merey <amerey@redhat.com>
|
||||
Date: Fri, 24 Jul 2020 15:16:20 -0400
|
||||
Subject: [PATCH] config/debuginfod.m4: Use PKG_CHECK_MODULES
|
||||
|
||||
Use PKG_CHECK_MODULES to set debuginfod autoconf vars. Also add
|
||||
pkg.m4 to config/.
|
||||
|
||||
ChangeLog:
|
||||
|
||||
* config/debuginfod.m4: use PKG_CHECK_MODULES.
|
||||
* config/pkg.m4: New file.
|
||||
* configure: Rebuild.
|
||||
* configure.ac: Remove AC_DEBUGINFOD.
|
||||
|
||||
ChangeLog/binutils:
|
||||
|
||||
* Makefile.am: Replace LIBDEBUGINFOD with DEBUGINFOD_LIBS.
|
||||
* Makefile.in: Rebuild.
|
||||
* configure: Rebuild.
|
||||
* doc/Makefile.in: Rebuild.
|
||||
|
||||
ChangeLog/gdb:
|
||||
|
||||
* Makefile.in: Replace LIBDEBUGINFOD with DEBUGINFOD_LIBS.
|
||||
* configure: Rebuild.
|
||||
|
||||
diff --git a/config/debuginfod.m4 b/config/debuginfod.m4
|
||||
--- a/config/debuginfod.m4
|
||||
+++ b/config/debuginfod.m4
|
||||
@@ -1,38 +1,30 @@
|
||||
-dnl Copyright (C) 1997-2019 Free Software Foundation, Inc.
|
||||
+dnl Copyright (C) 1997-2020 Free Software Foundation, Inc.
|
||||
dnl This file is free software, distributed under the terms of the GNU
|
||||
dnl General Public License. As a special exception to the GNU General
|
||||
dnl Public License, this file may be distributed as part of a program
|
||||
dnl that contains a configuration script generated by Autoconf, under
|
||||
dnl the same distribution terms as the rest of that program.
|
||||
|
||||
+m4_include([../config/pkg.m4])
|
||||
+
|
||||
AC_DEFUN([AC_DEBUGINFOD],
|
||||
[
|
||||
-# Enable debuginfod
|
||||
+# Handle optional debuginfod support
|
||||
AC_ARG_WITH([debuginfod],
|
||||
- AC_HELP_STRING([--with-debuginfod],
|
||||
- [Enable debuginfo lookups with debuginfod (auto/yes/no)]),
|
||||
- [], [with_debuginfod=auto])
|
||||
+ AC_HELP_STRING([--with-debuginfod], [Enable debuginfo lookups with debuginfod (auto/yes/no)]),
|
||||
+ [], [with_debuginfod=auto])
|
||||
AC_MSG_CHECKING([whether to use debuginfod])
|
||||
AC_MSG_RESULT([$with_debuginfod])
|
||||
|
||||
-if test "${with_debuginfod}" = no; then
|
||||
- AC_MSG_WARN([debuginfod support disabled; some features may be unavailable.])
|
||||
+if test "x$with_debuginfod" != xno; then
|
||||
+ PKG_CHECK_MODULES([DEBUGINFOD], [libdebuginfod >= 0.179],
|
||||
+ [AC_DEFINE([HAVE_LIBDEBUGINFOD], [1], [Define to 1 if debuginfod is enabled.])],
|
||||
+ [if test "x$with_debuginfod" = xyes; then
|
||||
+ AC_MSG_ERROR(["--with-debuginfod was given, but libdebuginfod is missing or unusable."])
|
||||
+ else
|
||||
+ AC_MSG_WARN([libdebuginfod is missing or unusable; some features may be unavailable.])
|
||||
+ fi])
|
||||
else
|
||||
- AC_CHECK_LIB([debuginfod], [debuginfod_begin], [have_debuginfod_lib=yes])
|
||||
- AC_CHECK_DECL([debuginfod_begin], [have_debuginfod_h=yes], [],
|
||||
- [#include <elfutils/debuginfod.h>])
|
||||
- if test "x$have_debuginfod_lib" = "xyes" -a \
|
||||
- "x$have_debuginfod_h" = "xyes"; then
|
||||
- AC_DEFINE([HAVE_LIBDEBUGINFOD], [1],
|
||||
- [Define to 1 if debuginfod is enabled.])
|
||||
- AC_SUBST([LIBDEBUGINFOD], ["-ldebuginfod"])
|
||||
- else
|
||||
- AC_SUBST([LIBDEBUGINFOD], [])
|
||||
- if test "$with_debuginfod" = yes; then
|
||||
- AC_MSG_ERROR([debuginfod is missing or unusable])
|
||||
- else
|
||||
- AC_MSG_WARN([debuginfod is missing or unusable; some features may be unavailable.])
|
||||
- fi
|
||||
- fi
|
||||
+ AC_MSG_WARN([debuginfod support disabled; some features may be unavailable.])
|
||||
fi
|
||||
])
|
||||
diff --git a/config/pkg.m4 b/config/pkg.m4
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
+++ b/config/pkg.m4
|
||||
@@ -0,0 +1,275 @@
|
||||
+# pkg.m4 - Macros to locate and utilise pkg-config. -*- Autoconf -*-
|
||||
+# serial 12 (pkg-config-0.29.2)
|
||||
+
|
||||
+dnl Copyright © 2004 Scott James Remnant <scott@netsplit.com>.
|
||||
+dnl Copyright © 2012-2015 Dan Nicholson <dbn.lists@gmail.com>
|
||||
+dnl
|
||||
+dnl This program is free software; you can redistribute it and/or modify
|
||||
+dnl it under the terms of the GNU General Public License as published by
|
||||
+dnl the Free Software Foundation; either version 2 of the License, or
|
||||
+dnl (at your option) any later version.
|
||||
+dnl
|
||||
+dnl This program is distributed in the hope that it will be useful, but
|
||||
+dnl WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
+dnl MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||
+dnl General Public License for more details.
|
||||
+dnl
|
||||
+dnl You should have received a copy of the GNU General Public License
|
||||
+dnl along with this program; if not, write to the Free Software
|
||||
+dnl Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
|
||||
+dnl 02111-1307, USA.
|
||||
+dnl
|
||||
+dnl As a special exception to the GNU General Public License, if you
|
||||
+dnl distribute this file as part of a program that contains a
|
||||
+dnl configuration script generated by Autoconf, you may include it under
|
||||
+dnl the same distribution terms that you use for the rest of that
|
||||
+dnl program.
|
||||
+
|
||||
+dnl PKG_PREREQ(MIN-VERSION)
|
||||
+dnl -----------------------
|
||||
+dnl Since: 0.29
|
||||
+dnl
|
||||
+dnl Verify that the version of the pkg-config macros are at least
|
||||
+dnl MIN-VERSION. Unlike PKG_PROG_PKG_CONFIG, which checks the user's
|
||||
+dnl installed version of pkg-config, this checks the developer's version
|
||||
+dnl of pkg.m4 when generating configure.
|
||||
+dnl
|
||||
+dnl To ensure that this macro is defined, also add:
|
||||
+dnl m4_ifndef([PKG_PREREQ],
|
||||
+dnl [m4_fatal([must install pkg-config 0.29 or later before running autoconf/autogen])])
|
||||
+dnl
|
||||
+dnl See the "Since" comment for each macro you use to see what version
|
||||
+dnl of the macros you require.
|
||||
+m4_defun([PKG_PREREQ],
|
||||
+[m4_define([PKG_MACROS_VERSION], [0.29.2])
|
||||
+m4_if(m4_version_compare(PKG_MACROS_VERSION, [$1]), -1,
|
||||
+ [m4_fatal([pkg.m4 version $1 or higher is required but ]PKG_MACROS_VERSION[ found])])
|
||||
+])dnl PKG_PREREQ
|
||||
+
|
||||
+dnl PKG_PROG_PKG_CONFIG([MIN-VERSION])
|
||||
+dnl ----------------------------------
|
||||
+dnl Since: 0.16
|
||||
+dnl
|
||||
+dnl Search for the pkg-config tool and set the PKG_CONFIG variable to
|
||||
+dnl first found in the path. Checks that the version of pkg-config found
|
||||
+dnl is at least MIN-VERSION. If MIN-VERSION is not specified, 0.9.0 is
|
||||
+dnl used since that's the first version where most current features of
|
||||
+dnl pkg-config existed.
|
||||
+AC_DEFUN([PKG_PROG_PKG_CONFIG],
|
||||
+[m4_pattern_forbid([^_?PKG_[A-Z_]+$])
|
||||
+m4_pattern_allow([^PKG_CONFIG(_(PATH|LIBDIR|SYSROOT_DIR|ALLOW_SYSTEM_(CFLAGS|LIBS)))?$])
|
||||
+m4_pattern_allow([^PKG_CONFIG_(DISABLE_UNINSTALLED|TOP_BUILD_DIR|DEBUG_SPEW)$])
|
||||
+AC_ARG_VAR([PKG_CONFIG], [path to pkg-config utility])
|
||||
+AC_ARG_VAR([PKG_CONFIG_PATH], [directories to add to pkg-config's search path])
|
||||
+AC_ARG_VAR([PKG_CONFIG_LIBDIR], [path overriding pkg-config's built-in search path])
|
||||
+
|
||||
+if test "x$ac_cv_env_PKG_CONFIG_set" != "xset"; then
|
||||
+ AC_PATH_TOOL([PKG_CONFIG], [pkg-config])
|
||||
+fi
|
||||
+if test -n "$PKG_CONFIG"; then
|
||||
+ _pkg_min_version=m4_default([$1], [0.9.0])
|
||||
+ AC_MSG_CHECKING([pkg-config is at least version $_pkg_min_version])
|
||||
+ if $PKG_CONFIG --atleast-pkgconfig-version $_pkg_min_version; then
|
||||
+ AC_MSG_RESULT([yes])
|
||||
+ else
|
||||
+ AC_MSG_RESULT([no])
|
||||
+ PKG_CONFIG=""
|
||||
+ fi
|
||||
+fi[]dnl
|
||||
+])dnl PKG_PROG_PKG_CONFIG
|
||||
+
|
||||
+dnl PKG_CHECK_EXISTS(MODULES, [ACTION-IF-FOUND], [ACTION-IF-NOT-FOUND])
|
||||
+dnl -------------------------------------------------------------------
|
||||
+dnl Since: 0.18
|
||||
+dnl
|
||||
+dnl Check to see whether a particular set of modules exists. Similar to
|
||||
+dnl PKG_CHECK_MODULES(), but does not set variables or print errors.
|
||||
+dnl
|
||||
+dnl Please remember that m4 expands AC_REQUIRE([PKG_PROG_PKG_CONFIG])
|
||||
+dnl only at the first occurence in configure.ac, so if the first place
|
||||
+dnl it's called might be skipped (such as if it is within an "if", you
|
||||
+dnl have to call PKG_CHECK_EXISTS manually
|
||||
+AC_DEFUN([PKG_CHECK_EXISTS],
|
||||
+[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl
|
||||
+if test -n "$PKG_CONFIG" && \
|
||||
+ AC_RUN_LOG([$PKG_CONFIG --exists --print-errors "$1"]); then
|
||||
+ m4_default([$2], [:])
|
||||
+m4_ifvaln([$3], [else
|
||||
+ $3])dnl
|
||||
+fi])
|
||||
+
|
||||
+dnl _PKG_CONFIG([VARIABLE], [COMMAND], [MODULES])
|
||||
+dnl ---------------------------------------------
|
||||
+dnl Internal wrapper calling pkg-config via PKG_CONFIG and setting
|
||||
+dnl pkg_failed based on the result.
|
||||
+m4_define([_PKG_CONFIG],
|
||||
+[if test -n "$$1"; then
|
||||
+ pkg_cv_[]$1="$$1"
|
||||
+ elif test -n "$PKG_CONFIG"; then
|
||||
+ PKG_CHECK_EXISTS([$3],
|
||||
+ [pkg_cv_[]$1=`$PKG_CONFIG --[]$2 "$3" 2>/dev/null`
|
||||
+ test "x$?" != "x0" && pkg_failed=yes ],
|
||||
+ [pkg_failed=yes])
|
||||
+ else
|
||||
+ pkg_failed=untried
|
||||
+fi[]dnl
|
||||
+])dnl _PKG_CONFIG
|
||||
+
|
||||
+dnl _PKG_SHORT_ERRORS_SUPPORTED
|
||||
+dnl ---------------------------
|
||||
+dnl Internal check to see if pkg-config supports short errors.
|
||||
+AC_DEFUN([_PKG_SHORT_ERRORS_SUPPORTED],
|
||||
+[AC_REQUIRE([PKG_PROG_PKG_CONFIG])
|
||||
+if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then
|
||||
+ _pkg_short_errors_supported=yes
|
||||
+else
|
||||
+ _pkg_short_errors_supported=no
|
||||
+fi[]dnl
|
||||
+])dnl _PKG_SHORT_ERRORS_SUPPORTED
|
||||
+
|
||||
+
|
||||
+dnl PKG_CHECK_MODULES(VARIABLE-PREFIX, MODULES, [ACTION-IF-FOUND],
|
||||
+dnl [ACTION-IF-NOT-FOUND])
|
||||
+dnl --------------------------------------------------------------
|
||||
+dnl Since: 0.4.0
|
||||
+dnl
|
||||
+dnl Note that if there is a possibility the first call to
|
||||
+dnl PKG_CHECK_MODULES might not happen, you should be sure to include an
|
||||
+dnl explicit call to PKG_PROG_PKG_CONFIG in your configure.ac
|
||||
+AC_DEFUN([PKG_CHECK_MODULES],
|
||||
+[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl
|
||||
+AC_ARG_VAR([$1][_CFLAGS], [C compiler flags for $1, overriding pkg-config])dnl
|
||||
+AC_ARG_VAR([$1][_LIBS], [linker flags for $1, overriding pkg-config])dnl
|
||||
+
|
||||
+pkg_failed=no
|
||||
+AC_MSG_CHECKING([for $2])
|
||||
+
|
||||
+_PKG_CONFIG([$1][_CFLAGS], [cflags], [$2])
|
||||
+_PKG_CONFIG([$1][_LIBS], [libs], [$2])
|
||||
+
|
||||
+m4_define([_PKG_TEXT], [Alternatively, you may set the environment variables $1[]_CFLAGS
|
||||
+and $1[]_LIBS to avoid the need to call pkg-config.
|
||||
+See the pkg-config man page for more details.])
|
||||
+
|
||||
+if test $pkg_failed = yes; then
|
||||
+ AC_MSG_RESULT([no])
|
||||
+ _PKG_SHORT_ERRORS_SUPPORTED
|
||||
+ if test $_pkg_short_errors_supported = yes; then
|
||||
+ $1[]_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "$2" 2>&1`
|
||||
+ else
|
||||
+ $1[]_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "$2" 2>&1`
|
||||
+ fi
|
||||
+ # Put the nasty error message in config.log where it belongs
|
||||
+ echo "$$1[]_PKG_ERRORS" >&AS_MESSAGE_LOG_FD
|
||||
+
|
||||
+ m4_default([$4], [AC_MSG_ERROR(
|
||||
+[Package requirements ($2) were not met:
|
||||
+
|
||||
+$$1_PKG_ERRORS
|
||||
+
|
||||
+Consider adjusting the PKG_CONFIG_PATH environment variable if you
|
||||
+installed software in a non-standard prefix.
|
||||
+
|
||||
+_PKG_TEXT])[]dnl
|
||||
+ ])
|
||||
+elif test $pkg_failed = untried; then
|
||||
+ AC_MSG_RESULT([no])
|
||||
+ m4_default([$4], [AC_MSG_FAILURE(
|
||||
+[The pkg-config script could not be found or is too old. Make sure it
|
||||
+is in your PATH or set the PKG_CONFIG environment variable to the full
|
||||
+path to pkg-config.
|
||||
+
|
||||
+_PKG_TEXT
|
||||
+
|
||||
+To get pkg-config, see <http://pkg-config.freedesktop.org/>.])[]dnl
|
||||
+ ])
|
||||
+else
|
||||
+ $1[]_CFLAGS=$pkg_cv_[]$1[]_CFLAGS
|
||||
+ $1[]_LIBS=$pkg_cv_[]$1[]_LIBS
|
||||
+ AC_MSG_RESULT([yes])
|
||||
+ $3
|
||||
+fi[]dnl
|
||||
+])dnl PKG_CHECK_MODULES
|
||||
+
|
||||
+
|
||||
+dnl PKG_CHECK_MODULES_STATIC(VARIABLE-PREFIX, MODULES, [ACTION-IF-FOUND],
|
||||
+dnl [ACTION-IF-NOT-FOUND])
|
||||
+dnl ---------------------------------------------------------------------
|
||||
+dnl Since: 0.29
|
||||
+dnl
|
||||
+dnl Checks for existence of MODULES and gathers its build flags with
|
||||
+dnl static libraries enabled. Sets VARIABLE-PREFIX_CFLAGS from --cflags
|
||||
+dnl and VARIABLE-PREFIX_LIBS from --libs.
|
||||
+dnl
|
||||
+dnl Note that if there is a possibility the first call to
|
||||
+dnl PKG_CHECK_MODULES_STATIC might not happen, you should be sure to
|
||||
+dnl include an explicit call to PKG_PROG_PKG_CONFIG in your
|
||||
+dnl configure.ac.
|
||||
+AC_DEFUN([PKG_CHECK_MODULES_STATIC],
|
||||
+[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl
|
||||
+_save_PKG_CONFIG=$PKG_CONFIG
|
||||
+PKG_CONFIG="$PKG_CONFIG --static"
|
||||
+PKG_CHECK_MODULES($@)
|
||||
+PKG_CONFIG=$_save_PKG_CONFIG[]dnl
|
||||
+])dnl PKG_CHECK_MODULES_STATIC
|
||||
+
|
||||
+
|
||||
+dnl PKG_INSTALLDIR([DIRECTORY])
|
||||
+dnl -------------------------
|
||||
+dnl Since: 0.27
|
||||
+dnl
|
||||
+dnl Substitutes the variable pkgconfigdir as the location where a module
|
||||
+dnl should install pkg-config .pc files. By default the directory is
|
||||
+dnl $libdir/pkgconfig, but the default can be changed by passing
|
||||
+dnl DIRECTORY. The user can override through the --with-pkgconfigdir
|
||||
+dnl parameter.
|
||||
+AC_DEFUN([PKG_INSTALLDIR],
|
||||
+[m4_pushdef([pkg_default], [m4_default([$1], ['${libdir}/pkgconfig'])])
|
||||
+m4_pushdef([pkg_description],
|
||||
+ [pkg-config installation directory @<:@]pkg_default[@:>@])
|
||||
+AC_ARG_WITH([pkgconfigdir],
|
||||
+ [AS_HELP_STRING([--with-pkgconfigdir], pkg_description)],,
|
||||
+ [with_pkgconfigdir=]pkg_default)
|
||||
+AC_SUBST([pkgconfigdir], [$with_pkgconfigdir])
|
||||
+m4_popdef([pkg_default])
|
||||
+m4_popdef([pkg_description])
|
||||
+])dnl PKG_INSTALLDIR
|
||||
+
|
||||
+
|
||||
+dnl PKG_NOARCH_INSTALLDIR([DIRECTORY])
|
||||
+dnl --------------------------------
|
||||
+dnl Since: 0.27
|
||||
+dnl
|
||||
+dnl Substitutes the variable noarch_pkgconfigdir as the location where a
|
||||
+dnl module should install arch-independent pkg-config .pc files. By
|
||||
+dnl default the directory is $datadir/pkgconfig, but the default can be
|
||||
+dnl changed by passing DIRECTORY. The user can override through the
|
||||
+dnl --with-noarch-pkgconfigdir parameter.
|
||||
+AC_DEFUN([PKG_NOARCH_INSTALLDIR],
|
||||
+[m4_pushdef([pkg_default], [m4_default([$1], ['${datadir}/pkgconfig'])])
|
||||
+m4_pushdef([pkg_description],
|
||||
+ [pkg-config arch-independent installation directory @<:@]pkg_default[@:>@])
|
||||
+AC_ARG_WITH([noarch-pkgconfigdir],
|
||||
+ [AS_HELP_STRING([--with-noarch-pkgconfigdir], pkg_description)],,
|
||||
+ [with_noarch_pkgconfigdir=]pkg_default)
|
||||
+AC_SUBST([noarch_pkgconfigdir], [$with_noarch_pkgconfigdir])
|
||||
+m4_popdef([pkg_default])
|
||||
+m4_popdef([pkg_description])
|
||||
+])dnl PKG_NOARCH_INSTALLDIR
|
||||
+
|
||||
+
|
||||
+dnl PKG_CHECK_VAR(VARIABLE, MODULE, CONFIG-VARIABLE,
|
||||
+dnl [ACTION-IF-FOUND], [ACTION-IF-NOT-FOUND])
|
||||
+dnl -------------------------------------------
|
||||
+dnl Since: 0.28
|
||||
+dnl
|
||||
+dnl Retrieves the value of the pkg-config variable for the given module.
|
||||
+AC_DEFUN([PKG_CHECK_VAR],
|
||||
+[AC_REQUIRE([PKG_PROG_PKG_CONFIG])dnl
|
||||
+AC_ARG_VAR([$1], [value of $3 for $2, overriding pkg-config])dnl
|
||||
+
|
||||
+_PKG_CONFIG([$1], [variable="][$3]["], [$2])
|
||||
+AS_VAR_COPY([$1], [pkg_cv_][$1])
|
||||
+
|
||||
+AS_VAR_IF([$1], [""], [$5], [$4])dnl
|
||||
+])dnl PKG_CHECK_VAR
|
||||
diff --git a/gdb/Makefile.in b/gdb/Makefile.in
|
||||
--- a/gdb/Makefile.in
|
||||
+++ b/gdb/Makefile.in
|
||||
@@ -587,7 +587,8 @@ INTERNAL_CFLAGS_BASE = \
|
||||
$(GDB_CFLAGS) $(OPCODES_CFLAGS) $(READLINE_CFLAGS) $(ZLIBINC) \
|
||||
$(BFD_CFLAGS) $(INCLUDE_CFLAGS) $(LIBDECNUMBER_CFLAGS) \
|
||||
$(INTL_CFLAGS) $(INCGNU) $(ENABLE_CFLAGS) $(INTERNAL_CPPFLAGS) \
|
||||
- $(SRCHIGH_CFLAGS) $(TOP_CFLAGS) $(PTHREAD_CFLAGS)
|
||||
+ $(SRCHIGH_CFLAGS) $(TOP_CFLAGS) $(PTHREAD_CFLAGS) \
|
||||
+ @DEBUGINFOD_CFLAGS@
|
||||
INTERNAL_WARN_CFLAGS = $(INTERNAL_CFLAGS_BASE) $(GDB_WARN_CFLAGS)
|
||||
INTERNAL_CFLAGS = $(INTERNAL_WARN_CFLAGS) $(GDB_WERROR_CFLAGS)
|
||||
|
||||
@@ -613,7 +614,7 @@ CLIBS = $(SIM) $(READLINE) $(OPCODES) $(BFD) $(LIBCTF) $(ZLIB) \
|
||||
$(LIBEXPAT) $(LIBLZMA) $(LIBBABELTRACE) $(LIBIPT) \
|
||||
$(LIBIBERTY) $(WIN32LIBS) $(LIBGNU) $(LIBICONV) $(LIBMPFR) \
|
||||
$(SRCHIGH_LIBS) $(LIBXXHASH) $(PTHREAD_LIBS) \
|
||||
- @LIBDEBUGINFOD@
|
||||
+ @DEBUGINFOD_LIBS@
|
||||
CDEPS = $(NAT_CDEPS) $(SIM) $(BFD) $(READLINE_DEPS) $(LIBCTF) \
|
||||
$(OPCODES) $(INTL_DEPS) $(LIBIBERTY) $(CONFIG_DEPS) $(LIBGNU)
|
||||
|
||||
diff --git a/gdb/configure b/gdb/configure
|
||||
--- a/gdb/configure
|
||||
+++ b/gdb/configure
|
||||
@@ -758,7 +758,11 @@ REPORT_BUGS_TEXI
|
||||
REPORT_BUGS_TO
|
||||
PKGVERSION
|
||||
CODESIGN_CERT
|
||||
-LIBDEBUGINFOD
|
||||
+DEBUGINFOD_LIBS
|
||||
+DEBUGINFOD_CFLAGS
|
||||
+PKG_CONFIG_LIBDIR
|
||||
+PKG_CONFIG_PATH
|
||||
+PKG_CONFIG
|
||||
HAVE_NATIVE_GCORE_TARGET
|
||||
TARGET_OBS
|
||||
subdirs
|
||||
@@ -937,6 +941,9 @@ MAKEINFOFLAGS
|
||||
PKG_CONFIG
|
||||
PKG_CONFIG_PATH
|
||||
PKG_CONFIG_LIBDIR
|
||||
+PKG_CONFIG_CFLAGS
|
||||
+DEBUGINFOD_CFLAGS
|
||||
+DEBUGINFOD_LIBS
|
||||
RPM_CFLAGS
|
||||
RPM_LIBS
|
||||
YACC
|
||||
@@ -1683,6 +1690,10 @@ Some influential environment variables:
|
||||
directories to add to pkg-config's search path
|
||||
PKG_CONFIG_LIBDIR
|
||||
path overriding pkg-config's built-in search path
|
||||
+ DEBUGINFOD_CFLAGS
|
||||
+ C compiler flags for DEBUGINFOD, overriding pkg-config
|
||||
+ DEBUGINFOD_LIBS
|
||||
+ linker flags for DEBUGINFOD, overriding pkg-config
|
||||
RPM_CFLAGS C compiler flags for RPM, overriding pkg-config
|
||||
RPM_LIBS linker flags for RPM, overriding pkg-config
|
||||
YACC The `Yet Another Compiler Compiler' implementation to use.
|
||||
@@ -2275,52 +2286,6 @@ rm -f conftest.val
|
||||
|
||||
} # ac_fn_c_compute_int
|
||||
|
||||
-# ac_fn_c_check_decl LINENO SYMBOL VAR INCLUDES
|
||||
-# ---------------------------------------------
|
||||
-# Tests whether SYMBOL is declared in INCLUDES, setting cache variable VAR
|
||||
-# accordingly.
|
||||
-ac_fn_c_check_decl ()
|
||||
-{
|
||||
- as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
|
||||
- as_decl_name=`echo $2|sed 's/ *(.*//'`
|
||||
- as_decl_use=`echo $2|sed -e 's/(/((/' -e 's/)/) 0&/' -e 's/,/) 0& (/g'`
|
||||
- { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $as_decl_name is declared" >&5
|
||||
-$as_echo_n "checking whether $as_decl_name is declared... " >&6; }
|
||||
-if eval \${$3+:} false; then :
|
||||
- $as_echo_n "(cached) " >&6
|
||||
-else
|
||||
- cat confdefs.h - <<_ACEOF >conftest.$ac_ext
|
||||
-/* end confdefs.h. */
|
||||
-$4
|
||||
-int
|
||||
-main ()
|
||||
-{
|
||||
-#ifndef $as_decl_name
|
||||
-#ifdef __cplusplus
|
||||
- (void) $as_decl_use;
|
||||
-#else
|
||||
- (void) $as_decl_name;
|
||||
-#endif
|
||||
-#endif
|
||||
-
|
||||
- ;
|
||||
- return 0;
|
||||
-}
|
||||
-_ACEOF
|
||||
-if ac_fn_c_try_compile "$LINENO"; then :
|
||||
- eval "$3=yes"
|
||||
-else
|
||||
- eval "$3=no"
|
||||
-fi
|
||||
-rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
|
||||
-fi
|
||||
-eval ac_res=\$$3
|
||||
- { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5
|
||||
-$as_echo "$ac_res" >&6; }
|
||||
- eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
|
||||
-
|
||||
-} # ac_fn_c_check_decl
|
||||
-
|
||||
# ac_fn_c_check_func LINENO FUNC VAR
|
||||
# ----------------------------------
|
||||
# Tests whether FUNC exists, setting the cache variable VAR accordingly
|
||||
@@ -2388,6 +2353,52 @@ $as_echo "$ac_res" >&6; }
|
||||
|
||||
} # ac_fn_c_check_func
|
||||
|
||||
+# ac_fn_c_check_decl LINENO SYMBOL VAR INCLUDES
|
||||
+# ---------------------------------------------
|
||||
+# Tests whether SYMBOL is declared in INCLUDES, setting cache variable VAR
|
||||
+# accordingly.
|
||||
+ac_fn_c_check_decl ()
|
||||
+{
|
||||
+ as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
|
||||
+ as_decl_name=`echo $2|sed 's/ *(.*//'`
|
||||
+ as_decl_use=`echo $2|sed -e 's/(/((/' -e 's/)/) 0&/' -e 's/,/) 0& (/g'`
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $as_decl_name is declared" >&5
|
||||
+$as_echo_n "checking whether $as_decl_name is declared... " >&6; }
|
||||
+if eval \${$3+:} false; then :
|
||||
+ $as_echo_n "(cached) " >&6
|
||||
+else
|
||||
+ cat confdefs.h - <<_ACEOF >conftest.$ac_ext
|
||||
+/* end confdefs.h. */
|
||||
+$4
|
||||
+int
|
||||
+main ()
|
||||
+{
|
||||
+#ifndef $as_decl_name
|
||||
+#ifdef __cplusplus
|
||||
+ (void) $as_decl_use;
|
||||
+#else
|
||||
+ (void) $as_decl_name;
|
||||
+#endif
|
||||
+#endif
|
||||
+
|
||||
+ ;
|
||||
+ return 0;
|
||||
+}
|
||||
+_ACEOF
|
||||
+if ac_fn_c_try_compile "$LINENO"; then :
|
||||
+ eval "$3=yes"
|
||||
+else
|
||||
+ eval "$3=no"
|
||||
+fi
|
||||
+rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
|
||||
+fi
|
||||
+eval ac_res=\$$3
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5
|
||||
+$as_echo "$ac_res" >&6; }
|
||||
+ eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
|
||||
+
|
||||
+} # ac_fn_c_check_decl
|
||||
+
|
||||
# ac_fn_c_check_member LINENO AGGR MEMBER VAR INCLUDES
|
||||
# ----------------------------------------------------
|
||||
# Tries to find if the field MEMBER exists in type AGGR, after including
|
||||
@@ -7338,7 +7349,127 @@ esac
|
||||
|
||||
# Handle optional debuginfod support
|
||||
|
||||
-# Enable debuginfod
|
||||
+
|
||||
+
|
||||
+
|
||||
+
|
||||
+
|
||||
+
|
||||
+if test "x$ac_cv_env_PKG_CONFIG_set" != "xset"; then
|
||||
+ if test -n "$ac_tool_prefix"; then
|
||||
+ # Extract the first word of "${ac_tool_prefix}pkg-config", so it can be a program name with args.
|
||||
+set dummy ${ac_tool_prefix}pkg-config; ac_word=$2
|
||||
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
|
||||
+$as_echo_n "checking for $ac_word... " >&6; }
|
||||
+if ${ac_cv_path_PKG_CONFIG+:} false; then :
|
||||
+ $as_echo_n "(cached) " >&6
|
||||
+else
|
||||
+ case $PKG_CONFIG in
|
||||
+ [\\/]* | ?:[\\/]*)
|
||||
+ ac_cv_path_PKG_CONFIG="$PKG_CONFIG" # Let the user override the test with a path.
|
||||
+ ;;
|
||||
+ *)
|
||||
+ as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
|
||||
+for as_dir in $PATH
|
||||
+do
|
||||
+ IFS=$as_save_IFS
|
||||
+ test -z "$as_dir" && as_dir=.
|
||||
+ for ac_exec_ext in '' $ac_executable_extensions; do
|
||||
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
|
||||
+ ac_cv_path_PKG_CONFIG="$as_dir/$ac_word$ac_exec_ext"
|
||||
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
|
||||
+ break 2
|
||||
+ fi
|
||||
+done
|
||||
+ done
|
||||
+IFS=$as_save_IFS
|
||||
+
|
||||
+ ;;
|
||||
+esac
|
||||
+fi
|
||||
+PKG_CONFIG=$ac_cv_path_PKG_CONFIG
|
||||
+if test -n "$PKG_CONFIG"; then
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $PKG_CONFIG" >&5
|
||||
+$as_echo "$PKG_CONFIG" >&6; }
|
||||
+else
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
|
||||
+$as_echo "no" >&6; }
|
||||
+fi
|
||||
+
|
||||
+
|
||||
+fi
|
||||
+if test -z "$ac_cv_path_PKG_CONFIG"; then
|
||||
+ ac_pt_PKG_CONFIG=$PKG_CONFIG
|
||||
+ # Extract the first word of "pkg-config", so it can be a program name with args.
|
||||
+set dummy pkg-config; ac_word=$2
|
||||
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
|
||||
+$as_echo_n "checking for $ac_word... " >&6; }
|
||||
+if ${ac_cv_path_ac_pt_PKG_CONFIG+:} false; then :
|
||||
+ $as_echo_n "(cached) " >&6
|
||||
+else
|
||||
+ case $ac_pt_PKG_CONFIG in
|
||||
+ [\\/]* | ?:[\\/]*)
|
||||
+ ac_cv_path_ac_pt_PKG_CONFIG="$ac_pt_PKG_CONFIG" # Let the user override the test with a path.
|
||||
+ ;;
|
||||
+ *)
|
||||
+ as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
|
||||
+for as_dir in $PATH
|
||||
+do
|
||||
+ IFS=$as_save_IFS
|
||||
+ test -z "$as_dir" && as_dir=.
|
||||
+ for ac_exec_ext in '' $ac_executable_extensions; do
|
||||
+ if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
|
||||
+ ac_cv_path_ac_pt_PKG_CONFIG="$as_dir/$ac_word$ac_exec_ext"
|
||||
+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
|
||||
+ break 2
|
||||
+ fi
|
||||
+done
|
||||
+ done
|
||||
+IFS=$as_save_IFS
|
||||
+
|
||||
+ ;;
|
||||
+esac
|
||||
+fi
|
||||
+ac_pt_PKG_CONFIG=$ac_cv_path_ac_pt_PKG_CONFIG
|
||||
+if test -n "$ac_pt_PKG_CONFIG"; then
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_pt_PKG_CONFIG" >&5
|
||||
+$as_echo "$ac_pt_PKG_CONFIG" >&6; }
|
||||
+else
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
|
||||
+$as_echo "no" >&6; }
|
||||
+fi
|
||||
+
|
||||
+ if test "x$ac_pt_PKG_CONFIG" = x; then
|
||||
+ PKG_CONFIG=""
|
||||
+ else
|
||||
+ case $cross_compiling:$ac_tool_warned in
|
||||
+yes:)
|
||||
+{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5
|
||||
+$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;}
|
||||
+ac_tool_warned=yes ;;
|
||||
+esac
|
||||
+ PKG_CONFIG=$ac_pt_PKG_CONFIG
|
||||
+ fi
|
||||
+else
|
||||
+ PKG_CONFIG="$ac_cv_path_PKG_CONFIG"
|
||||
+fi
|
||||
+
|
||||
+fi
|
||||
+if test -n "$PKG_CONFIG"; then
|
||||
+ _pkg_min_version=0.9.0
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: checking pkg-config is at least version $_pkg_min_version" >&5
|
||||
+$as_echo_n "checking pkg-config is at least version $_pkg_min_version... " >&6; }
|
||||
+ if $PKG_CONFIG --atleast-pkgconfig-version $_pkg_min_version; then
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
|
||||
+$as_echo "yes" >&6; }
|
||||
+ else
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
|
||||
+$as_echo "no" >&6; }
|
||||
+ PKG_CONFIG=""
|
||||
+ fi
|
||||
+fi
|
||||
+
|
||||
+# Handle optional debuginfod support
|
||||
|
||||
# Check whether --with-debuginfod was given.
|
||||
if test "${with_debuginfod+set}" = set; then :
|
||||
@@ -7352,72 +7483,93 @@ $as_echo_n "checking whether to use debuginfod... " >&6; }
|
||||
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_debuginfod" >&5
|
||||
$as_echo "$with_debuginfod" >&6; }
|
||||
|
||||
-if test "${with_debuginfod}" = no; then
|
||||
- { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: debuginfod support disabled; some features may be unavailable." >&5
|
||||
-$as_echo "$as_me: WARNING: debuginfod support disabled; some features may be unavailable." >&2;}
|
||||
-else
|
||||
- { $as_echo "$as_me:${as_lineno-$LINENO}: checking for debuginfod_begin in -ldebuginfod" >&5
|
||||
-$as_echo_n "checking for debuginfod_begin in -ldebuginfod... " >&6; }
|
||||
-if ${ac_cv_lib_debuginfod_debuginfod_begin+:} false; then :
|
||||
- $as_echo_n "(cached) " >&6
|
||||
-else
|
||||
- ac_check_lib_save_LIBS=$LIBS
|
||||
-LIBS="-ldebuginfod $LIBS"
|
||||
-cat confdefs.h - <<_ACEOF >conftest.$ac_ext
|
||||
-/* end confdefs.h. */
|
||||
+if test "x$with_debuginfod" != xno; then
|
||||
|
||||
-/* Override any GCC internal prototype to avoid an error.
|
||||
- Use char because int might match the return type of a GCC
|
||||
- builtin and then its argument prototype would still apply. */
|
||||
-#ifdef __cplusplus
|
||||
-extern "C"
|
||||
-#endif
|
||||
-char debuginfod_begin ();
|
||||
-int
|
||||
-main ()
|
||||
-{
|
||||
-return debuginfod_begin ();
|
||||
- ;
|
||||
- return 0;
|
||||
-}
|
||||
-_ACEOF
|
||||
-if ac_fn_c_try_link "$LINENO"; then :
|
||||
- ac_cv_lib_debuginfod_debuginfod_begin=yes
|
||||
+pkg_failed=no
|
||||
+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for libdebuginfod >= 0.179" >&5
|
||||
+$as_echo_n "checking for libdebuginfod >= 0.179... " >&6; }
|
||||
+
|
||||
+if test -n "$DEBUGINFOD_CFLAGS"; then
|
||||
+ pkg_cv_DEBUGINFOD_CFLAGS="$DEBUGINFOD_CFLAGS"
|
||||
+ elif test -n "$PKG_CONFIG"; then
|
||||
+ if test -n "$PKG_CONFIG" && \
|
||||
+ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"libdebuginfod >= 0.179\""; } >&5
|
||||
+ ($PKG_CONFIG --exists --print-errors "libdebuginfod >= 0.179") 2>&5
|
||||
+ ac_status=$?
|
||||
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
|
||||
+ test $ac_status = 0; }; then
|
||||
+ pkg_cv_DEBUGINFOD_CFLAGS=`$PKG_CONFIG --cflags "libdebuginfod >= 0.179" 2>/dev/null`
|
||||
+ test "x$?" != "x0" && pkg_failed=yes
|
||||
else
|
||||
- ac_cv_lib_debuginfod_debuginfod_begin=no
|
||||
+ pkg_failed=yes
|
||||
fi
|
||||
-rm -f core conftest.err conftest.$ac_objext \
|
||||
- conftest$ac_exeext conftest.$ac_ext
|
||||
-LIBS=$ac_check_lib_save_LIBS
|
||||
+ else
|
||||
+ pkg_failed=untried
|
||||
+fi
|
||||
+if test -n "$DEBUGINFOD_LIBS"; then
|
||||
+ pkg_cv_DEBUGINFOD_LIBS="$DEBUGINFOD_LIBS"
|
||||
+ elif test -n "$PKG_CONFIG"; then
|
||||
+ if test -n "$PKG_CONFIG" && \
|
||||
+ { { $as_echo "$as_me:${as_lineno-$LINENO}: \$PKG_CONFIG --exists --print-errors \"libdebuginfod >= 0.179\""; } >&5
|
||||
+ ($PKG_CONFIG --exists --print-errors "libdebuginfod >= 0.179") 2>&5
|
||||
+ ac_status=$?
|
||||
+ $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5
|
||||
+ test $ac_status = 0; }; then
|
||||
+ pkg_cv_DEBUGINFOD_LIBS=`$PKG_CONFIG --libs "libdebuginfod >= 0.179" 2>/dev/null`
|
||||
+ test "x$?" != "x0" && pkg_failed=yes
|
||||
+else
|
||||
+ pkg_failed=yes
|
||||
fi
|
||||
-{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_debuginfod_debuginfod_begin" >&5
|
||||
-$as_echo "$ac_cv_lib_debuginfod_debuginfod_begin" >&6; }
|
||||
-if test "x$ac_cv_lib_debuginfod_debuginfod_begin" = xyes; then :
|
||||
- have_debuginfod_lib=yes
|
||||
+ else
|
||||
+ pkg_failed=untried
|
||||
fi
|
||||
|
||||
- ac_fn_c_check_decl "$LINENO" "debuginfod_begin" "ac_cv_have_decl_debuginfod_begin" "#include <elfutils/debuginfod.h>
|
||||
-"
|
||||
-if test "x$ac_cv_have_decl_debuginfod_begin" = xyes; then :
|
||||
- have_debuginfod_h=yes
|
||||
-fi
|
||||
|
||||
- if test "x$have_debuginfod_lib" = "xyes" -a \
|
||||
- "x$have_debuginfod_h" = "xyes"; then
|
||||
|
||||
-$as_echo "#define HAVE_LIBDEBUGINFOD 1" >>confdefs.h
|
||||
+if test $pkg_failed = yes; then
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
|
||||
+$as_echo "no" >&6; }
|
||||
|
||||
- LIBDEBUGINFOD="-ldebuginfod"
|
||||
+if $PKG_CONFIG --atleast-pkgconfig-version 0.20; then
|
||||
+ _pkg_short_errors_supported=yes
|
||||
+else
|
||||
+ _pkg_short_errors_supported=no
|
||||
+fi
|
||||
+ if test $_pkg_short_errors_supported = yes; then
|
||||
+ DEBUGINFOD_PKG_ERRORS=`$PKG_CONFIG --short-errors --print-errors --cflags --libs "libdebuginfod >= 0.179" 2>&1`
|
||||
+ else
|
||||
+ DEBUGINFOD_PKG_ERRORS=`$PKG_CONFIG --print-errors --cflags --libs "libdebuginfod >= 0.179" 2>&1`
|
||||
+ fi
|
||||
+ # Put the nasty error message in config.log where it belongs
|
||||
+ echo "$DEBUGINFOD_PKG_ERRORS" >&5
|
||||
|
||||
- else
|
||||
+ if test "x$with_debuginfod" = xyes; then
|
||||
+ as_fn_error $? "\"--with-debuginfod was given, but libdebuginfod is missing or unusable.\"" "$LINENO" 5
|
||||
+ else
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: libdebuginfod is missing or unusable; some features may be unavailable." >&5
|
||||
+$as_echo "$as_me: WARNING: libdebuginfod is missing or unusable; some features may be unavailable." >&2;}
|
||||
+ fi
|
||||
+elif test $pkg_failed = untried; then
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
|
||||
+$as_echo "no" >&6; }
|
||||
+ if test "x$with_debuginfod" = xyes; then
|
||||
+ as_fn_error $? "\"--with-debuginfod was given, but libdebuginfod is missing or unusable.\"" "$LINENO" 5
|
||||
+ else
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: libdebuginfod is missing or unusable; some features may be unavailable." >&5
|
||||
+$as_echo "$as_me: WARNING: libdebuginfod is missing or unusable; some features may be unavailable." >&2;}
|
||||
+ fi
|
||||
+else
|
||||
+ DEBUGINFOD_CFLAGS=$pkg_cv_DEBUGINFOD_CFLAGS
|
||||
+ DEBUGINFOD_LIBS=$pkg_cv_DEBUGINFOD_LIBS
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5
|
||||
+$as_echo "yes" >&6; }
|
||||
|
||||
- if test "$with_debuginfod" = yes; then
|
||||
- as_fn_error $? "debuginfod is missing or unusable" "$LINENO" 5
|
||||
- else
|
||||
- { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: debuginfod is missing or unusable; some features may be unavailable." >&5
|
||||
-$as_echo "$as_me: WARNING: debuginfod is missing or unusable; some features may be unavailable." >&2;}
|
||||
- fi
|
||||
- fi
|
||||
+$as_echo "#define HAVE_LIBDEBUGINFOD 1" >>confdefs.h
|
||||
+
|
||||
+fi
|
||||
+else
|
||||
+ { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: debuginfod support disabled; some features may be unavailable." >&5
|
||||
+$as_echo "$as_me: WARNING: debuginfod support disabled; some features may be unavailable." >&2;}
|
||||
fi
|
||||
|
||||
|
@ -857,13 +857,13 @@ diff --git a/gdb/elfread.c b/gdb/elfread.c
|
||||
+ has_dwarf2 = true;
|
||||
+ }
|
||||
+ }
|
||||
+ /* Check if any separate debug info has been extracted out. */
|
||||
+ else if (bfd_get_section_by_name (objfile->obfd, ".gnu_debuglink")
|
||||
+ != NULL)
|
||||
+ debug_print_missing (objfile_name (objfile), build_id_filename.get ());
|
||||
+ else
|
||||
+ has_dwarf2 = false;
|
||||
+ }
|
||||
+ /* Check if any separate debug info has been extracted out. */
|
||||
+ else if (bfd_get_section_by_name (objfile->obfd, ".gnu_debuglink")
|
||||
+ != NULL)
|
||||
+ debug_print_missing (objfile_name (objfile), build_id_filename.get ());
|
||||
+ else
|
||||
+ has_dwarf2 = false;
|
||||
+ }
|
||||
}
|
||||
|
||||
@ -919,7 +919,7 @@ diff --git a/gdb/testsuite/gdb.debuginfod/fetch_src_and_symbols.exp b/gdb/testsu
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
+++ b/gdb/testsuite/gdb.debuginfod/fetch_src_and_symbols.exp
|
||||
@@ -0,0 +1,214 @@
|
||||
@@ -0,0 +1,246 @@
|
||||
+# Copyright 2020 Free Software Foundation, Inc.
|
||||
+
|
||||
+# This program is free software; you can redistribute it and/or modify
|
||||
@ -952,7 +952,8 @@ new file mode 100644
|
||||
+}
|
||||
+
|
||||
+# Skip testing if gdb was not configured with debuginfod
|
||||
+if { [string first "with-debuginfod" [exec $GDB --configuration]] == -1 } {
|
||||
+if { [string first "with-debuginfod" \
|
||||
+ [eval exec $GDB $INTERNAL_GDBFLAGS --configuration]] == -1 } {
|
||||
+ untested "gdb not configured with debuginfod"
|
||||
+ return -1
|
||||
+}
|
||||
@ -979,31 +980,6 @@ new file mode 100644
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+setenv DEBUGINFOD_URLS ""
|
||||
+setenv DEBUGINFOD_TIMEOUT 30
|
||||
+setenv DEBUGINFOD_CACHE_PATH $cache
|
||||
+
|
||||
+# Test that gdb cannot find source without debuginfod
|
||||
+clean_restart $binfile
|
||||
+gdb_test_no_output "set substitute-path $outputdir /dev/null"
|
||||
+gdb_test "list" ".*No such file or directory.*"
|
||||
+
|
||||
+# Strip symbols into separate file and move it so gdb cannot find it without debuginfod
|
||||
+if { [gdb_gnu_strip_debug $binfile ""] != 0 } {
|
||||
+ fail "strip debuginfo"
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+set debugdir [standard_output_file "debug"]
|
||||
+set debuginfo [standard_output_file "fetch_src_and_symbols.debug"]
|
||||
+
|
||||
+file mkdir $debugdir
|
||||
+file rename -force $debuginfo $debugdir
|
||||
+
|
||||
+# Test that gdb cannot find symbols without debuginfod
|
||||
+clean_restart $binfile
|
||||
+gdb_test "file" ".*No symbol file.*"
|
||||
+
|
||||
+# Write some assembly that just has a .gnu_debugaltlink section.
|
||||
+# Copied from testsuite/gdb.dwarf2/dwzbuildid.exp.
|
||||
+proc write_just_debugaltlink {filename dwzname buildid} {
|
||||
@ -1039,7 +1015,7 @@ new file mode 100644
|
||||
+
|
||||
+ cu {} {
|
||||
+ compile_unit {{language @DW_LANG_C}} {
|
||||
+ int_label2: base_type {
|
||||
+ int_label2: base_type {
|
||||
+ {name int}
|
||||
+ {byte_size 4 sdata}
|
||||
+ {encoding @DW_ATE_signed}
|
||||
@ -1055,85 +1031,141 @@ new file mode 100644
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
+set buildid "01234567890abcdef0123456"
|
||||
+proc no_url { } {
|
||||
+ global binfile outputdir debugdir
|
||||
+
|
||||
+write_just_debugaltlink ${binfile}_has_altlink.S ${binfile}_dwz.o $buildid
|
||||
+write_dwarf_file ${binfile}_dwz.S $buildid
|
||||
+ setenv DEBUGINFOD_URLS ""
|
||||
+
|
||||
+if {[gdb_compile ${binfile}_has_altlink.S ${binfile}_alt.o object nodebug] != ""} {
|
||||
+ fail "compile main with altlink"
|
||||
+ return -1
|
||||
+}
|
||||
+ # Test that gdb cannot find source without debuginfod
|
||||
+ clean_restart $binfile
|
||||
+ gdb_test_no_output "set substitute-path $outputdir /dev/null" \
|
||||
+ "set substitute-path"
|
||||
+ gdb_test "list" ".*No such file or directory.*"
|
||||
+
|
||||
+if {[gdb_compile ${binfile}_dwz.S ${binfile}_dwz.o object nodebug] != ""} {
|
||||
+ fail "compile altlink"
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+file rename -force ${binfile}_dwz.o $debugdir
|
||||
+
|
||||
+# Test that gdb cannot find dwz without debuginfod.
|
||||
+clean_restart
|
||||
+gdb_test "file ${binfile}_alt.o" ".*could not find '.gnu_debugaltlink'.*"
|
||||
+
|
||||
+# Find an unused port
|
||||
+set port 7999
|
||||
+set found 0
|
||||
+while { ! $found } {
|
||||
+ incr port
|
||||
+ if { $port == 65536 } {
|
||||
+ fail "no available ports"
|
||||
+ return -1
|
||||
+ }
|
||||
+
|
||||
+ spawn debuginfod -vvvv -d $db -p $port -F $debugdir
|
||||
+ expect {
|
||||
+ "started http server on IPv4 IPv6 port=$port" { set found 1 }
|
||||
+ "failed to bind to port" { kill_wait_spawned_process $spawn_id }
|
||||
+ timeout {
|
||||
+ fail "find port timeout"
|
||||
+ return -1
|
||||
+ }
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
+set metrics [list "ready 1" \
|
||||
+ "thread_work_total{role=\"traverse\"} 1" \
|
||||
+ "thread_work_pending{role=\"scan\"} 0" \
|
||||
+ "thread_busy{role=\"scan\"} 0"]
|
||||
+
|
||||
+# Check server metrics to confirm init has completed.
|
||||
+foreach m $metrics {
|
||||
+ set timelim 20
|
||||
+ while { $timelim != 0 } {
|
||||
+ sleep 0.5
|
||||
+ catch {exec curl -s http://127.0.0.1:$port/metrics} got
|
||||
+
|
||||
+ if { [regexp $m $got] } {
|
||||
+ break
|
||||
+ # Strip symbols into separate file and move it so gdb cannot find it \
|
||||
+ without debuginfod
|
||||
+ if { [gdb_gnu_strip_debug $binfile ""] != 0 } {
|
||||
+ fail "strip debuginfo"
|
||||
+ return -1
|
||||
+ }
|
||||
+
|
||||
+ incr timelim -1
|
||||
+ }
|
||||
+ set debugdir [standard_output_file "debug"]
|
||||
+ set debuginfo [standard_output_file "fetch_src_and_symbols.debug"]
|
||||
+
|
||||
+ if { $timelim == 0 } {
|
||||
+ fail "server init timeout"
|
||||
+ break
|
||||
+ }
|
||||
+ file mkdir $debugdir
|
||||
+ file rename -force $debuginfo $debugdir
|
||||
+
|
||||
+ # Test that gdb cannot find symbols without debuginfod
|
||||
+ clean_restart $binfile
|
||||
+ gdb_test "file" ".*No symbol file.*"
|
||||
+
|
||||
+ set buildid "01234567890abcdef0123456"
|
||||
+
|
||||
+ write_just_debugaltlink ${binfile}_has_altlink.S ${binfile}_dwz.o \
|
||||
+ $buildid
|
||||
+ write_dwarf_file ${binfile}_dwz.S $buildid
|
||||
+
|
||||
+ if {[gdb_compile ${binfile}_has_altlink.S ${binfile}_alt.o object \
|
||||
+ nodebug] != ""} {
|
||||
+ fail "compile main with altlink"
|
||||
+ return -1
|
||||
+ }
|
||||
+
|
||||
+ if {[gdb_compile ${binfile}_dwz.S ${binfile}_dwz.o object \
|
||||
+ nodebug] != ""} {
|
||||
+ fail "compile altlink"
|
||||
+ return -1
|
||||
+ }
|
||||
+
|
||||
+ file rename -force ${binfile}_dwz.o $debugdir
|
||||
+
|
||||
+ # Test that gdb cannot find dwz without debuginfod.
|
||||
+ clean_restart
|
||||
+ gdb_test "file ${binfile}_alt.o" \
|
||||
+ ".*could not find '.gnu_debugaltlink'.*" \
|
||||
+ "file [file tail ${binfile}_alt.o]"
|
||||
+}
|
||||
+
|
||||
+# Point the client to the server
|
||||
+setenv DEBUGINFOD_URLS http://127.0.0.1:$port
|
||||
+proc local_url { } {
|
||||
+ global binfile outputdir db debugdir
|
||||
+
|
||||
+# gdb should now find the symbol and source files
|
||||
+clean_restart $binfile
|
||||
+gdb_test_no_output "set substitute-path $outputdir /dev/null"
|
||||
+gdb_test "br main" "Breakpoint 1 at.*file.*"
|
||||
+gdb_test "l" ".*This program is distributed in the hope.*"
|
||||
+ # Find an unused port
|
||||
+ set port 7999
|
||||
+ set found 0
|
||||
+ while { ! $found } {
|
||||
+ incr port
|
||||
+ if { $port == 65536 } {
|
||||
+ fail "no available ports"
|
||||
+ return -1
|
||||
+ }
|
||||
+
|
||||
+# gdb should now find the debugaltlink file
|
||||
+clean_restart
|
||||
+gdb_test "file ${binfile}_alt.o" ".*Reading symbols from ${binfile}_alt.o\.\.\.*"
|
||||
+ spawn debuginfod -vvvv -d $db -p $port -F $debugdir
|
||||
+ expect {
|
||||
+ "started http server on IPv4 IPv6 port=$port" { set found 1 }
|
||||
+ "failed to bind to port" { kill_wait_spawned_process $spawn_id }
|
||||
+ timeout {
|
||||
+ fail "find port timeout"
|
||||
+ return -1
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ set metrics [list "ready 1" \
|
||||
+ "thread_work_total{role=\"traverse\"} 1" \
|
||||
+ "thread_work_pending{role=\"scan\"} 0" \
|
||||
+ "thread_busy{role=\"scan\"} 0"]
|
||||
+
|
||||
+ # Check server metrics to confirm init has completed.
|
||||
+ foreach m $metrics {
|
||||
+ set timelim 20
|
||||
+ while { $timelim != 0 } {
|
||||
+ sleep 0.5
|
||||
+ catch {exec curl -s http://127.0.0.1:$port/metrics} got
|
||||
+
|
||||
+ if { [regexp $m $got] } {
|
||||
+ break
|
||||
+ }
|
||||
+
|
||||
+ incr timelim -1
|
||||
+ }
|
||||
+
|
||||
+ if { $timelim == 0 } {
|
||||
+ fail "server init timeout"
|
||||
+ return -1
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ # Point the client to the server
|
||||
+ setenv DEBUGINFOD_URLS http://127.0.0.1:$port
|
||||
+
|
||||
+ # gdb should now find the symbol and source files
|
||||
+ clean_restart $binfile
|
||||
+ gdb_test_no_output "set substitute-path $outputdir /dev/null" \
|
||||
+ "set substitute-path"
|
||||
+ gdb_test "br main" "Breakpoint 1 at.*file.*"
|
||||
+ gdb_test "l" ".*This program is distributed in the hope.*"
|
||||
+
|
||||
+ # gdb should now find the debugaltlink file
|
||||
+ clean_restart
|
||||
+ gdb_test "file ${binfile}_alt.o" \
|
||||
+ ".*Reading symbols from ${binfile}_alt.o\.\.\.*" \
|
||||
+ "file [file tail ${binfile}_alt.o]"
|
||||
+}
|
||||
+
|
||||
+set envlist \
|
||||
+ [list \
|
||||
+ env(DEBUGINFOD_URLS) \
|
||||
+ env(DEBUGINFOD_TIMEOUT) \
|
||||
+ env(DEBUGINFOD_CACHE_PATH)]
|
||||
+
|
||||
+save_vars $envlist {
|
||||
+ setenv DEBUGINFOD_TIMEOUT 30
|
||||
+ setenv DEBUGINFOD_CACHE_PATH $cache
|
||||
+
|
||||
+ with_test_prefix no_url no_url
|
||||
+
|
||||
+ with_test_prefix local_url local_url
|
||||
+}
|
||||
diff --git a/gdb/testsuite/gdb.debuginfod/main.c b/gdb/testsuite/gdb.debuginfod/main.c
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
|
121
SOURCES/gdb-rhbz1842691-corefile-mem-access-10of15.patch
Normal file
121
SOURCES/gdb-rhbz1842691-corefile-mem-access-10of15.patch
Normal file
@ -0,0 +1,121 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 27 Jul 2020 19:38:20 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-10of15.patch
|
||||
|
||||
;; gcore command: Place all file-backed mappings in NT_FILE note
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Wed Jul 1 06:34:50 2020 -0700
|
||||
|
||||
gcore command: Place all file-backed mappings in NT_FILE note
|
||||
|
||||
When making a core file with the GDB's gcore command on Linux,
|
||||
the same criteria used for determining which mappings should be
|
||||
dumped were also being used for determining which entries should
|
||||
be placed in the NT_FILE note. This is wrong; we want to place
|
||||
all file-backed mappings in this note.
|
||||
|
||||
The predicate function, dump_mapping_p, was used to determine whether
|
||||
or not to dump a mapping from within linux_find_memory_regions_full.
|
||||
This commit leaves this predicate in place, but adds a new parameter,
|
||||
should_dump_mapping_p, to linux_find_memory_regions_full. It then
|
||||
calls should_dump_mapping_p instead of dump_mapping_p. dump_mapping_p
|
||||
is passed to linux_find_memory_regions_full at one call site; at the
|
||||
other call site, dump_note_entry_p is passed instead.
|
||||
|
||||
gdb/ChangeLog:
|
||||
|
||||
* linux-tdep.c (dump_note_entry_p): New function.
|
||||
(linux_dump_mapping_p_ftype): New typedef.
|
||||
(linux_find_memory_regions_full): Add new parameter,
|
||||
should_dump_mapping_p.
|
||||
(linux_find_memory_regions): Adjust call to
|
||||
linux_find_memory_regions_full.
|
||||
(linux_make_mappings_core_file_notes): Use dump_note_entry_p in
|
||||
call to linux_find_memory_regions_full.
|
||||
|
||||
diff --git a/gdb/linux-tdep.c b/gdb/linux-tdep.c
|
||||
--- a/gdb/linux-tdep.c
|
||||
+++ b/gdb/linux-tdep.c
|
||||
@@ -732,6 +732,25 @@ dump_mapping_p (filter_flags filterflags, const struct smaps_vmflags *v,
|
||||
return dump_p;
|
||||
}
|
||||
|
||||
+/* As above, but return true only when we should dump the NT_FILE
|
||||
+ entry. */
|
||||
+
|
||||
+static int
|
||||
+dump_note_entry_p (filter_flags filterflags, const struct smaps_vmflags *v,
|
||||
+ int maybe_private_p, int mapping_anon_p, int mapping_file_p,
|
||||
+ const char *filename, ULONGEST addr, ULONGEST offset)
|
||||
+{
|
||||
+ /* vDSO and vsyscall mappings will end up in the core file. Don't
|
||||
+ put them in the NT_FILE note. */
|
||||
+ if (strcmp ("[vdso]", filename) == 0
|
||||
+ || strcmp ("[vsyscall]", filename) == 0)
|
||||
+ return 0;
|
||||
+
|
||||
+ /* Otherwise, any other file-based mapping should be placed in the
|
||||
+ note. */
|
||||
+ return filename != nullptr;
|
||||
+}
|
||||
+
|
||||
/* Implement the "info proc" command. */
|
||||
|
||||
static void
|
||||
@@ -1246,10 +1265,20 @@ typedef int linux_find_memory_region_ftype (ULONGEST vaddr, ULONGEST size,
|
||||
const char *filename,
|
||||
void *data);
|
||||
|
||||
+typedef int linux_dump_mapping_p_ftype (filter_flags filterflags,
|
||||
+ const struct smaps_vmflags *v,
|
||||
+ int maybe_private_p,
|
||||
+ int mapping_anon_p,
|
||||
+ int mapping_file_p,
|
||||
+ const char *filename,
|
||||
+ ULONGEST addr,
|
||||
+ ULONGEST offset);
|
||||
+
|
||||
/* List memory regions in the inferior for a corefile. */
|
||||
|
||||
static int
|
||||
linux_find_memory_regions_full (struct gdbarch *gdbarch,
|
||||
+ linux_dump_mapping_p_ftype *should_dump_mapping_p,
|
||||
linux_find_memory_region_ftype *func,
|
||||
void *obfd)
|
||||
{
|
||||
@@ -1400,9 +1429,10 @@ linux_find_memory_regions_full (struct gdbarch *gdbarch,
|
||||
}
|
||||
|
||||
if (has_anonymous)
|
||||
- should_dump_p = dump_mapping_p (filterflags, &v, priv,
|
||||
- mapping_anon_p, mapping_file_p,
|
||||
- filename, addr, offset);
|
||||
+ should_dump_p = should_dump_mapping_p (filterflags, &v, priv,
|
||||
+ mapping_anon_p,
|
||||
+ mapping_file_p,
|
||||
+ filename, addr, offset);
|
||||
else
|
||||
{
|
||||
/* Older Linux kernels did not support the "Anonymous:" counter.
|
||||
@@ -1466,6 +1496,7 @@ linux_find_memory_regions (struct gdbarch *gdbarch,
|
||||
data.obfd = obfd;
|
||||
|
||||
return linux_find_memory_regions_full (gdbarch,
|
||||
+ dump_mapping_p,
|
||||
linux_find_memory_regions_thunk,
|
||||
&data);
|
||||
}
|
||||
@@ -1561,7 +1592,9 @@ linux_make_mappings_corefile_notes (struct gdbarch *gdbarch, bfd *obfd,
|
||||
pack_long (buf, long_type, 1);
|
||||
obstack_grow (&data_obstack, buf, TYPE_LENGTH (long_type));
|
||||
|
||||
- linux_find_memory_regions_full (gdbarch, linux_make_mappings_callback,
|
||||
+ linux_find_memory_regions_full (gdbarch,
|
||||
+ dump_note_entry_p,
|
||||
+ linux_make_mappings_callback,
|
||||
&mapping_data);
|
||||
|
||||
if (mapping_data.file_count != 0)
|
87
SOURCES/gdb-rhbz1842691-corefile-mem-access-11of15.patch
Normal file
87
SOURCES/gdb-rhbz1842691-corefile-mem-access-11of15.patch
Normal file
@ -0,0 +1,87 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Tue, 28 Jul 2020 09:26:44 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-11of15.patch
|
||||
|
||||
;; Adjust coredump-filter.exp to account for NT_FILE note handling
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Fri Jul 3 20:10:22 2020 -0700
|
||||
|
||||
Adjust coredump-filter.exp to account for NT_FILE note handling
|
||||
|
||||
This commit makes adjustments to coredump-filter.exp to account
|
||||
for the fact that NT_FILE file-backed mappings are now available
|
||||
when a core file is loaded. Thus, a test which was expected
|
||||
to PASS when a memory region was determined to be unavailable
|
||||
(due to no file-backed mappings being available) will now FAIL
|
||||
due to those mappings being available from having loaded the
|
||||
NT_FILE note.
|
||||
|
||||
I had originally marked the test as XFAIL, but Mihails Strasuns
|
||||
suggested a much better approach:
|
||||
|
||||
1) First test that it still works if file is accessible in the
|
||||
filesystem.
|
||||
2) Temporarily move / rename the file and test that disassembly
|
||||
doesn't work anymore.
|
||||
|
||||
That's what this commit implements.
|
||||
|
||||
gdb/testsuite/ChangeLog:
|
||||
|
||||
* gdb.base/coredump-filter.exp: Add second
|
||||
non-Private-Shared-Anon-File test.
|
||||
(test_disasm): Rename binfile for test which is expected
|
||||
to fail.
|
||||
|
||||
diff --git a/gdb/testsuite/gdb.base/coredump-filter.exp b/gdb/testsuite/gdb.base/coredump-filter.exp
|
||||
--- a/gdb/testsuite/gdb.base/coredump-filter.exp
|
||||
+++ b/gdb/testsuite/gdb.base/coredump-filter.exp
|
||||
@@ -80,15 +80,26 @@ proc do_load_and_test_core { core var working_var working_value dump_excluded }
|
||||
# disassemble of a function (i.e., the binary's .text section). GDB
|
||||
# should fail in this case. However, it must succeed if the binary is
|
||||
# provided along with the corefile. This is what we test here.
|
||||
+#
|
||||
+# A further complication is that Linux NT_FILE notes are now read from
|
||||
+# the corefile. This note allows GDB to find the binary for file
|
||||
+# backed mappings even though the binary wasn't loaded by GDB in the
|
||||
+# conventional manner. In order to see the expected failure for this
|
||||
+# case, we rename the binary in order to perform this test.
|
||||
|
||||
proc test_disasm { core address should_fail } {
|
||||
- global testfile hex
|
||||
+ global testfile hex binfile
|
||||
|
||||
# Restart GDB without loading the binary.
|
||||
with_test_prefix "no binary" {
|
||||
gdb_exit
|
||||
gdb_start
|
||||
|
||||
+ set hide_binfile [standard_output_file "${testfile}.hide"]
|
||||
+ if { $should_fail == 1 } {
|
||||
+ remote_exec host "mv -f $binfile $hide_binfile"
|
||||
+ }
|
||||
+
|
||||
set core_loaded [gdb_core_cmd "$core" "load core"]
|
||||
if { $core_loaded == -1 } {
|
||||
fail "loading $core"
|
||||
@@ -96,6 +107,7 @@ proc test_disasm { core address should_fail } {
|
||||
}
|
||||
|
||||
if { $should_fail == 1 } {
|
||||
+ remote_exec host "mv -f $hide_binfile $binfile"
|
||||
gdb_test "x/i \$pc" "=> $hex:\tCannot access memory at address $hex" \
|
||||
"disassemble function with corefile and without a binary"
|
||||
} else {
|
||||
@@ -225,5 +237,9 @@ foreach item $all_anon_corefiles {
|
||||
}
|
||||
|
||||
with_test_prefix "loading and testing corefile for non-Private-Shared-Anon-File" {
|
||||
+ test_disasm $non_private_shared_anon_file_core $main_addr 0
|
||||
+}
|
||||
+
|
||||
+with_test_prefix "loading and testing corefile for non-Private-Shared-Anon-File with renamed binary" {
|
||||
test_disasm $non_private_shared_anon_file_core $main_addr 1
|
||||
}
|
177
SOURCES/gdb-rhbz1842691-corefile-mem-access-12of15.patch
Normal file
177
SOURCES/gdb-rhbz1842691-corefile-mem-access-12of15.patch
Normal file
@ -0,0 +1,177 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Tue, 28 Jul 2020 09:32:50 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-12of15.patch
|
||||
|
||||
;; Add new command "maint print core-file-backed-mappings"
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Fri Jul 3 21:55:51 2020 -0700
|
||||
|
||||
Add new command "maint print core-file-backed-mappings"
|
||||
|
||||
I wrote a read_core_file_mappings method for FreeBSD and then registered
|
||||
this gdbarch method. I saw some strange behavior while testing it and
|
||||
wanted a way to make sure that mappings were being correctly loaded
|
||||
into corelow.c, so I wrote the new command which is the topic of this
|
||||
commit. I think it might be occasionally useful for debugging strange
|
||||
corefile behavior.
|
||||
|
||||
With regard to FreeBSD, my work isn't ready yet. Unlike Linux,
|
||||
FreeBSD puts all mappings into its core file note. And, unlike Linux,
|
||||
it doesn't dump load segments which occupy no space in the file. So
|
||||
my (perhaps naive) implementation of a FreeBSD read_core_file_mappings
|
||||
didn't work all that well: I saw more failures in the corefile2.exp
|
||||
tests than without it. I think it should be possible to make FreeBSD
|
||||
work as well as Linux, but it will require doing something with all of
|
||||
the mappings, not just the file based mappings that I was considering.
|
||||
|
||||
In the v4 series, Pedro asked the following:
|
||||
|
||||
I don't understand what this command provides that "info proc
|
||||
mappings" doesn't? Can you give an example of when you'd use this
|
||||
command over "info proc mappings" ?
|
||||
|
||||
On Linux, "info proc mappings" and "maint print core-file-backed-mappings"
|
||||
will produce similar, possibly identical, output. This need not be
|
||||
the case for other OSes. E.g. on FreeBSD, had I finished the
|
||||
implementation, the output from these commands would have been very
|
||||
different. The FreeBSD "info proc mappings" command would show
|
||||
additional (non-file-backed) mappings in addition to at least one
|
||||
additional field (memory permissions) for each mapping.
|
||||
|
||||
As noted earlier, I was seeing some unexpected behavior while working
|
||||
on the FreeBSD implementation and wanted to be certain that the
|
||||
mappings were being correctly loaded by corelow.c. "info proc
|
||||
mappings" prints the core file mappings, but doesn't tell us anything
|
||||
about whether they've been loaded by corelow.c This new maintenance
|
||||
command directly interrogates the data structures and prints the
|
||||
values found there.
|
||||
|
||||
gdb/ChangeLog:
|
||||
|
||||
* corelow.c (gdbcmd.h): Include.
|
||||
(core_target::info_proc_mappings): New method.
|
||||
(get_current_core_target): New function.
|
||||
(maintenance_print_core_file_backed_mappings): New function.
|
||||
(_initialize_corelow): Add core-file-backed-mappings to
|
||||
"maint print" commands.
|
||||
|
||||
diff --git a/gdb/corelow.c b/gdb/corelow.c
|
||||
--- a/gdb/corelow.c
|
||||
+++ b/gdb/corelow.c
|
||||
@@ -51,6 +51,7 @@
|
||||
#include "build-id.h"
|
||||
#include "gdbsupport/pathstuff.h"
|
||||
#include <unordered_map>
|
||||
+#include "gdbcmd.h"
|
||||
|
||||
#ifndef O_LARGEFILE
|
||||
#define O_LARGEFILE 0
|
||||
@@ -121,6 +122,9 @@ public:
|
||||
const char *human_name,
|
||||
bool required);
|
||||
|
||||
+ /* See definition. */
|
||||
+ void info_proc_mappings (struct gdbarch *gdbarch);
|
||||
+
|
||||
private: /* per-core data */
|
||||
|
||||
/* The core's section table. Note that these target sections are
|
||||
@@ -1170,6 +1174,86 @@ core_target::info_proc (const char *args, enum info_proc_what request)
|
||||
return true;
|
||||
}
|
||||
|
||||
+/* Get a pointer to the current core target. If not connected to a
|
||||
+ core target, return NULL. */
|
||||
+
|
||||
+static core_target *
|
||||
+get_current_core_target ()
|
||||
+{
|
||||
+ target_ops *proc_target = find_target_at (process_stratum);
|
||||
+ return dynamic_cast<core_target *> (proc_target);
|
||||
+}
|
||||
+
|
||||
+/* Display file backed mappings from core file. */
|
||||
+
|
||||
+void
|
||||
+core_target::info_proc_mappings (struct gdbarch *gdbarch)
|
||||
+{
|
||||
+ if (m_core_file_mappings.sections != m_core_file_mappings.sections_end)
|
||||
+ {
|
||||
+ printf_filtered (_("Mapped address spaces:\n\n"));
|
||||
+ if (gdbarch_addr_bit (gdbarch) == 32)
|
||||
+ {
|
||||
+ printf_filtered ("\t%10s %10s %10s %10s %s\n",
|
||||
+ "Start Addr",
|
||||
+ " End Addr",
|
||||
+ " Size", " Offset", "objfile");
|
||||
+ }
|
||||
+ else
|
||||
+ {
|
||||
+ printf_filtered (" %18s %18s %10s %10s %s\n",
|
||||
+ "Start Addr",
|
||||
+ " End Addr",
|
||||
+ " Size", " Offset", "objfile");
|
||||
+ }
|
||||
+ }
|
||||
+
|
||||
+ for (const struct target_section *tsp = m_core_file_mappings.sections;
|
||||
+ tsp < m_core_file_mappings.sections_end;
|
||||
+ tsp++)
|
||||
+ {
|
||||
+ ULONGEST start = tsp->addr;
|
||||
+ ULONGEST end = tsp->endaddr;
|
||||
+ ULONGEST file_ofs = tsp->the_bfd_section->filepos;
|
||||
+ const char *filename = bfd_get_filename (tsp->the_bfd_section->owner);
|
||||
+
|
||||
+ if (gdbarch_addr_bit (gdbarch) == 32)
|
||||
+ printf_filtered ("\t%10s %10s %10s %10s %s\n",
|
||||
+ paddress (gdbarch, start),
|
||||
+ paddress (gdbarch, end),
|
||||
+ hex_string (end - start),
|
||||
+ hex_string (file_ofs),
|
||||
+ filename);
|
||||
+ else
|
||||
+ printf_filtered (" %18s %18s %10s %10s %s\n",
|
||||
+ paddress (gdbarch, start),
|
||||
+ paddress (gdbarch, end),
|
||||
+ hex_string (end - start),
|
||||
+ hex_string (file_ofs),
|
||||
+ filename);
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
+/* Implement "maintenance print core-file-backed-mappings" command.
|
||||
+
|
||||
+ If mappings are loaded, the results should be similar to the
|
||||
+ mappings shown by "info proc mappings". This command is mainly a
|
||||
+ debugging tool for GDB developers to make sure that the expected
|
||||
+ mappings are present after loading a core file. For Linux, the
|
||||
+ output provided by this command will be very similar (if not
|
||||
+ identical) to that provided by "info proc mappings". This is not
|
||||
+ necessarily the case for other OSes which might provide
|
||||
+ more/different information in the "info proc mappings" output. */
|
||||
+
|
||||
+static void
|
||||
+maintenance_print_core_file_backed_mappings (const char *args, int from_tty)
|
||||
+{
|
||||
+ core_target *targ = get_current_core_target ();
|
||||
+ if (targ != nullptr)
|
||||
+ targ->info_proc_mappings (targ->core_gdbarch ());
|
||||
+}
|
||||
+
|
||||
+void _initialize_corelow ();
|
||||
void
|
||||
_initialize_corelow (void)
|
||||
{
|
||||
@@ -1181,4 +1265,8 @@ Set whether CORE-FILE loads the build-id associated files automatically."), _("\
|
||||
Show whether CORE-FILE loads the build-id associated files automatically."),
|
||||
NULL, NULL, NULL,
|
||||
&setlist, &showlist);
|
||||
+ add_cmd ("core-file-backed-mappings", class_maintenance,
|
||||
+ maintenance_print_core_file_backed_mappings,
|
||||
+ _("Print core file's file-backed mappings"),
|
||||
+ &maintenanceprintlist);
|
||||
}
|
41
SOURCES/gdb-rhbz1842691-corefile-mem-access-13of15.patch
Normal file
41
SOURCES/gdb-rhbz1842691-corefile-mem-access-13of15.patch
Normal file
@ -0,0 +1,41 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Tue, 28 Jul 2020 09:44:04 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-13of15.patch
|
||||
|
||||
;; Add documentation for "maint print core-file-backed-mappings"
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Fri Jul 3 22:09:20 2020 -0700
|
||||
|
||||
Add documentation for "maint print core-file-backed-mappings"
|
||||
|
||||
gdb/ChangeLog:
|
||||
|
||||
* NEWS (New commands): Mention new command
|
||||
"maintenance print core-file-backed-mappings".
|
||||
|
||||
gdb/doc/ChangeLog:
|
||||
|
||||
* gdb.texinfo (Maintenance Commands): Add documentation for
|
||||
new command "maintenance print core-file-backed-mappings".
|
||||
|
||||
diff --git a/gdb/doc/gdb.texinfo b/gdb/doc/gdb.texinfo
|
||||
--- a/gdb/doc/gdb.texinfo
|
||||
+++ b/gdb/doc/gdb.texinfo
|
||||
@@ -38268,6 +38268,14 @@ library. This exercises all @code{libthread_db} functionality used by
|
||||
@code{libthread_db} uses. Note that parts of the test may be skipped
|
||||
on some platforms when debugging core files.
|
||||
|
||||
+@kindex maint print core-file-backed-mappings
|
||||
+@cindex memory address space mappings
|
||||
+@item maint print core-file-backed-mappings
|
||||
+Print the file-backed mappings which were loaded from a core file note.
|
||||
+This output represents state internal to @value{GDBN} and should be
|
||||
+similar to the mappings displayed by the @code{info proc mappings}
|
||||
+command.
|
||||
+
|
||||
@kindex maint print dummy-frames
|
||||
@item maint print dummy-frames
|
||||
Prints the contents of @value{GDBN}'s internal dummy-frame stack.
|
439
SOURCES/gdb-rhbz1842691-corefile-mem-access-14of15.patch
Normal file
439
SOURCES/gdb-rhbz1842691-corefile-mem-access-14of15.patch
Normal file
@ -0,0 +1,439 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Tue, 28 Jul 2020 09:46:44 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-14of15.patch
|
||||
|
||||
;; New core file tests with mappings over existing program memory
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Wed Jun 17 19:25:47 2020 -0700
|
||||
|
||||
New core file tests with mappings over existing program memory
|
||||
|
||||
This test case was inspired by Pedro's demonstration of a problem
|
||||
with my v2 patches. It can be found here:
|
||||
|
||||
https://sourceware.org/pipermail/gdb-patches/2020-May/168826.html
|
||||
|
||||
In a nutshell, my earlier patches could not handle the case in
|
||||
which a read-only mapping created with mmap() was created at
|
||||
an address used by other file-backed read-only memory in use by
|
||||
the process.
|
||||
|
||||
This problem has been fixed (for Linux, anyway) by the commit "Use
|
||||
NT_FILE note section for reading core target memory".
|
||||
|
||||
When I run this test without any of my recent corefile patches,
|
||||
I see these failures:
|
||||
|
||||
FAIL: gdb.base/corefile2.exp: kernel core: print/x mbuf_ro[0]@4
|
||||
FAIL: gdb.base/corefile2.exp: kernel core: print/x mbuf_ro[pagesize-4]@4
|
||||
FAIL: gdb.base/corefile2.exp: kernel core: print/x mbuf_ro[-3]@6
|
||||
FAIL: gdb.base/corefile2.exp: kernel core: print/x mbuf_rw[pagesize-3]@6
|
||||
FAIL: gdb.base/corefile2.exp: kernel core: print/x mbuf_ro[pagesize-3]@6
|
||||
FAIL: gdb.base/corefile2.exp: maint print core-file-backed-mappings
|
||||
FAIL: gdb.base/corefile2.exp: gcore core: print/x mbuf_ro[-3]@6
|
||||
|
||||
The ones involving mbuf_ro will almost certainly fail when run on
|
||||
non-Linux systems; I've used setup_xfail on those tests to prevent
|
||||
them from outright FAILing when not run on Linux. For a time, I
|
||||
had considered skipping these tests altogether when not run on
|
||||
Linux, but I changed my mind due to this failure...
|
||||
|
||||
FAIL: gdb.base/corefile2.exp: print/x mbuf_rw[pagesize-3]@6
|
||||
|
||||
I think it *should* pass without my recent corefile patches. The fact
|
||||
that it doesn't is likely due to a bug in GDB. The following
|
||||
interaction with GDB demonstrates the problem:
|
||||
|
||||
(gdb) print/x mbuf_rw[pagesize-3]@6
|
||||
$1 = {0x0, 0x0, 0x0, 0x0, 0x0, 0x0}
|
||||
(gdb) print/x mbuf_rw[pagesize]@3
|
||||
$2 = {0x6b, 0x6b, 0x6b}
|
||||
|
||||
The last three values in display of $1 should be the same as those
|
||||
shown by $2. Like this...
|
||||
|
||||
(gdb) print/x mbuf_rw[pagesize-3]@6
|
||||
$1 = {0x0, 0x0, 0x0, 0x6b, 0x6b, 0x6b}
|
||||
(gdb) print/x mbuf_rw[pagesize]@3
|
||||
$2 = {0x6b, 0x6b, 0x6b}
|
||||
|
||||
That latter output was obtained with the use of all of my current
|
||||
corefile patches. I see no failures on Linux when running this test
|
||||
with my current set of corefile patches. I tested 3 architectures:
|
||||
x86_64, s390x, and aarch64.
|
||||
|
||||
I also tested on FreeBSD 12.1-RELEASE. I see the following results
|
||||
both with and without the current set of core file patches:
|
||||
|
||||
# of expected passes 26
|
||||
# of expected failures 8
|
||||
|
||||
Of particular interest is that I did *not* see the problematic mbuf_rw
|
||||
failure noted earlier (both with and without the core file patches).
|
||||
I still don't have an explanation for why this failure occurred on
|
||||
Linux. Prior to running the tests, I had hypothesized that I'd see
|
||||
this failure on FreeBSD too, but testing shows that this is not the
|
||||
case.
|
||||
|
||||
Also of importance is that we see no FAILs with this test on FreeBSD
|
||||
which indicates that I XFAILed the correct tests.
|
||||
|
||||
This version runs the interesting tests twice, once with a kernel
|
||||
created core file and another time with a gcore created core file.
|
||||
|
||||
It also does a very minimal test of the new command "maint print
|
||||
core-file-backed-mappings".
|
||||
|
||||
gdb/testsuite/ChangeLog:
|
||||
|
||||
* gdb.base/corefile2.exp: New file.
|
||||
* gdb.base/coremaker2.exp: New file.
|
||||
|
||||
diff --git a/gdb/testsuite/gdb.base/corefile2.exp b/gdb/testsuite/gdb.base/corefile2.exp
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
+++ b/gdb/testsuite/gdb.base/corefile2.exp
|
||||
@@ -0,0 +1,185 @@
|
||||
+# Copyright 2020 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/>.
|
||||
+
|
||||
+# Tests of core file memory accesses when mmap() has been used to
|
||||
+# create a "hole" of zeroes over pre-existing memory regions. See
|
||||
+# coremaker2.c for details.
|
||||
+
|
||||
+# are we on a target board
|
||||
+if ![isnative] then {
|
||||
+ return
|
||||
+}
|
||||
+
|
||||
+# Some of these tests will only work on GNU/Linux due to the
|
||||
+# fact that Linux core files includes a section describing
|
||||
+# memory address to file mappings. We'll use set_up_xfail for the
|
||||
+# affected tests. As other targets become supported, the condition
|
||||
+# can be changed accordingly.
|
||||
+
|
||||
+set xfail 0
|
||||
+if { ![istarget *-linux*] } {
|
||||
+ set xfail 1
|
||||
+}
|
||||
+
|
||||
+standard_testfile coremaker2.c
|
||||
+
|
||||
+if {[build_executable $testfile.exp $testfile $srcfile debug] == -1} {
|
||||
+ untested "failed to compile"
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+set corefile [core_find $binfile {}]
|
||||
+if {$corefile == ""} {
|
||||
+ return 0
|
||||
+}
|
||||
+
|
||||
+gdb_start
|
||||
+gdb_reinitialize_dir $srcdir/$subdir
|
||||
+gdb_load ${binfile}
|
||||
+
|
||||
+# Attempt to load the core file.
|
||||
+
|
||||
+gdb_test_multiple "core-file $corefile" "core-file command" {
|
||||
+ -re ".* program is being debugged already.*y or n. $" {
|
||||
+ # gdb_load may connect us to a gdbserver.
|
||||
+ send_gdb "y\n"
|
||||
+ exp_continue
|
||||
+ }
|
||||
+ -re "Core was generated by .*corefile.*\r\n\#0 .*\(\).*\r\n$gdb_prompt $" {
|
||||
+ pass "core-file command"
|
||||
+ }
|
||||
+ -re "Core was generated by .*\r\n\#0 .*\(\).*\r\n$gdb_prompt $" {
|
||||
+ pass "core-file command (with bad program name)"
|
||||
+ }
|
||||
+ -re ".*registers from core file: File in wrong format.* $" {
|
||||
+ fail "core-file command (could not read registers from core file)"
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
+# Perform the "interesting" tests which check the contents of certain
|
||||
+# memory regions.
|
||||
+
|
||||
+proc do_tests { } {
|
||||
+ global xfail
|
||||
+
|
||||
+ # Check contents of beginning of buf_rw and buf_ro.
|
||||
+
|
||||
+ gdb_test {print/x buf_rw[0]@4} {\{0x6b, 0x6b, 0x6b, 0x6b\}}
|
||||
+ gdb_test {print/x buf_ro[0]@4} {\{0xc5, 0xc5, 0xc5, 0xc5\}}
|
||||
+
|
||||
+ # Check for correct contents at beginning of mbuf_rw and mbuf_ro.
|
||||
+
|
||||
+ gdb_test {print/x mbuf_rw[0]@4} {\{0x0, 0x0, 0x0, 0x0\}}
|
||||
+
|
||||
+ if { $xfail } { setup_xfail "*-*-*" }
|
||||
+ gdb_test {print/x mbuf_ro[0]@4} {\{0x0, 0x0, 0x0, 0x0\}}
|
||||
+
|
||||
+ # Check contents of mbuf_rw and mbuf_ro at the end of these regions.
|
||||
+
|
||||
+ gdb_test {print/x mbuf_rw[pagesize-4]@4} {\{0x0, 0x0, 0x0, 0x0\}}
|
||||
+
|
||||
+ if { $xfail } { setup_xfail "*-*-*" }
|
||||
+ gdb_test {print/x mbuf_ro[pagesize-4]@4} {\{0x0, 0x0, 0x0, 0x0\}}
|
||||
+
|
||||
+ # Check contents of mbuf_rw and mbuf_ro, right before the hole,
|
||||
+ # overlapping into the beginning of these mmap'd regions.
|
||||
+
|
||||
+ gdb_test {print/x mbuf_rw[-3]@6} {\{0x6b, 0x6b, 0x6b, 0x0, 0x0, 0x0\}}
|
||||
+
|
||||
+ if { $xfail } { setup_xfail "*-*-*" }
|
||||
+ gdb_test {print/x mbuf_ro[-3]@6} {\{0xc5, 0xc5, 0xc5, 0x0, 0x0, 0x0\}}
|
||||
+
|
||||
+ # Likewise, at the end of the mbuf_rw and mbuf_ro, with overlap.
|
||||
+
|
||||
+ # If this test FAILs, it's probably a genuine bug unrelated to whether
|
||||
+ # the core file includes a section describing memory address to file
|
||||
+ # mappings or not. (So don't xfail it!)
|
||||
+ gdb_test {print/x mbuf_rw[pagesize-3]@6} {\{0x0, 0x0, 0x0, 0x6b, 0x6b, 0x6b\}}
|
||||
+
|
||||
+ if { $xfail } { setup_xfail "*-*-*" }
|
||||
+ gdb_test {print/x mbuf_ro[pagesize-3]@6} {\{0x0, 0x0, 0x0, 0xc5, 0xc5, 0xc5\}}
|
||||
+
|
||||
+ # Check contents of (what should be) buf_rw and buf_ro immediately after
|
||||
+ # mbuf_rw and mbuf_ro holes.
|
||||
+
|
||||
+ gdb_test {print/x mbuf_rw[pagesize]@4} {\{0x6b, 0x6b, 0x6b, 0x6b\}}
|
||||
+ gdb_test {print/x mbuf_ro[pagesize]@4} {\{0xc5, 0xc5, 0xc5, 0xc5\}}
|
||||
+
|
||||
+ # Check contents at ends of buf_rw and buf_rw.
|
||||
+
|
||||
+ gdb_test {print/x buf_rw[sizeof(buf_rw)-4]@4} {\{0x6b, 0x6b, 0x6b, 0x6b\}}
|
||||
+ gdb_test {print/x buf_ro[sizeof(buf_ro)-4]@4} {\{0xc5, 0xc5, 0xc5, 0xc5\}}
|
||||
+}
|
||||
+
|
||||
+# Run tests with kernel-produced core file.
|
||||
+
|
||||
+with_test_prefix "kernel core" {
|
||||
+ do_tests
|
||||
+}
|
||||
+
|
||||
+# Verify that "maint print core-file-backed-mappings" exists and does
|
||||
+# not crash GDB. If it produces any output at all, make sure that
|
||||
+# that output at least mentions binfile.
|
||||
+
|
||||
+set test "maint print core-file-backed-mappings"
|
||||
+gdb_test_multiple $test "" {
|
||||
+ -re ".*$binfile.*$gdb_prompt $" {
|
||||
+ pass $test
|
||||
+ }
|
||||
+ -re "^$test\[\r\n\]*$gdb_prompt $" {
|
||||
+ pass "$test (no output)"
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
+# Restart and run to the abort call.
|
||||
+
|
||||
+clean_restart $binfile
|
||||
+
|
||||
+if ![runto_main] then {
|
||||
+ fail "can't run to main"
|
||||
+ return
|
||||
+}
|
||||
+
|
||||
+gdb_breakpoint [gdb_get_line_number "abort"]
|
||||
+gdb_continue_to_breakpoint "at abort"
|
||||
+
|
||||
+# Do not execute abort call; instead, invoke gcore command to make a
|
||||
+# gdb-produced core file.
|
||||
+
|
||||
+set corefile [standard_output_file gcore.test]
|
||||
+set core_supported [gdb_gcore_cmd "$corefile" "save a corefile"]
|
||||
+if {!$core_supported} {
|
||||
+ return
|
||||
+}
|
||||
+
|
||||
+# maint print-core-file-backed-mappings shouldn't produce any output
|
||||
+# when not debugging a core file.
|
||||
+
|
||||
+gdb_test_no_output "maint print core-file-backed-mappings" \
|
||||
+ "maint print core-file-backed-mapping with no core file"
|
||||
+
|
||||
+clean_restart $binfile
|
||||
+
|
||||
+set core_loaded [gdb_core_cmd "$corefile" "re-load generated corefile"]
|
||||
+if { $core_loaded == -1 } {
|
||||
+ # No use proceeding from here.
|
||||
+ return
|
||||
+}
|
||||
+
|
||||
+# Run tests using gcore-produced core file.
|
||||
+
|
||||
+with_test_prefix "gcore core" {
|
||||
+ do_tests
|
||||
+}
|
||||
diff --git a/gdb/testsuite/gdb.base/coremaker2.c b/gdb/testsuite/gdb.base/coremaker2.c
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
+++ b/gdb/testsuite/gdb.base/coremaker2.c
|
||||
@@ -0,0 +1,150 @@
|
||||
+/* Copyright 1992-2020 Free Software Foundation, Inc.
|
||||
+
|
||||
+ This file is part of GDB.
|
||||
+
|
||||
+ 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/>. */
|
||||
+
|
||||
+/* This test has two large memory areas buf_rw and buf_ro.
|
||||
+
|
||||
+ buf_rw is written to by the program while buf_ro is initialized at
|
||||
+ compile / load time. Thus, when a core file is created, buf_rw's
|
||||
+ memory should reside in the core file, but buf_ro probably won't be.
|
||||
+ Instead, the contents of buf_ro are available from the executable.
|
||||
+
|
||||
+ Now, for the wrinkle: We create a one page read-only mapping over
|
||||
+ both of these areas. This will create a one page "hole" of all
|
||||
+ zeros in each area.
|
||||
+
|
||||
+ Will GDB be able to correctly read memory from each of the four
|
||||
+ (or six, if you count the regions on the other side of each hole)
|
||||
+ memory regions? */
|
||||
+
|
||||
+#include <stdio.h>
|
||||
+#include <sys/types.h>
|
||||
+#include <fcntl.h>
|
||||
+#include <sys/mman.h>
|
||||
+#include <signal.h>
|
||||
+#include <stdlib.h>
|
||||
+#include <unistd.h>
|
||||
+#include <string.h>
|
||||
+#include <errno.h>
|
||||
+
|
||||
+/* These are globals so that we can find them easily when debugging
|
||||
+ the core file. */
|
||||
+long pagesize;
|
||||
+unsigned long long addr;
|
||||
+char *mbuf_ro;
|
||||
+char *mbuf_rw;
|
||||
+
|
||||
+/* 24 KiB buffer. */
|
||||
+char buf_rw[24 * 1024];
|
||||
+
|
||||
+/* 24 KiB worth of data. For this test case, we can't allocate a
|
||||
+ buffer and then fill it; we want GDB to have to read this data
|
||||
+ from the executable; it should NOT find it in the core file. */
|
||||
+
|
||||
+#define C5_16 \
|
||||
+ 0xc5, 0xc5, 0xc5, 0xc5, \
|
||||
+ 0xc5, 0xc5, 0xc5, 0xc5, \
|
||||
+ 0xc5, 0xc5, 0xc5, 0xc5, \
|
||||
+ 0xc5, 0xc5, 0xc5, 0xc5
|
||||
+
|
||||
+#define C5_256 \
|
||||
+ C5_16, C5_16, C5_16, C5_16, \
|
||||
+ C5_16, C5_16, C5_16, C5_16, \
|
||||
+ C5_16, C5_16, C5_16, C5_16, \
|
||||
+ C5_16, C5_16, C5_16, C5_16
|
||||
+
|
||||
+#define C5_1k \
|
||||
+ C5_256, C5_256, C5_256, C5_256
|
||||
+
|
||||
+#define C5_24k \
|
||||
+ C5_1k, C5_1k, C5_1k, C5_1k, \
|
||||
+ C5_1k, C5_1k, C5_1k, C5_1k, \
|
||||
+ C5_1k, C5_1k, C5_1k, C5_1k, \
|
||||
+ C5_1k, C5_1k, C5_1k, C5_1k, \
|
||||
+ C5_1k, C5_1k, C5_1k, C5_1k, \
|
||||
+ C5_1k, C5_1k, C5_1k, C5_1k
|
||||
+
|
||||
+const char buf_ro[] = { C5_24k };
|
||||
+
|
||||
+int
|
||||
+main (int argc, char **argv)
|
||||
+{
|
||||
+ int i, bitcount;
|
||||
+
|
||||
+#ifdef _SC_PAGESIZE
|
||||
+ pagesize = sysconf (_SC_PAGESIZE);
|
||||
+#else
|
||||
+ pagesize = 8192;
|
||||
+#endif
|
||||
+
|
||||
+ /* Verify that pagesize is a power of 2. */
|
||||
+ bitcount = 0;
|
||||
+ for (i = 0; i < 4 * sizeof (pagesize); i++)
|
||||
+ if (pagesize & (1 << i))
|
||||
+ bitcount++;
|
||||
+
|
||||
+ if (bitcount != 1)
|
||||
+ {
|
||||
+ fprintf (stderr, "pagesize is not a power of 2.\n");
|
||||
+ exit (1);
|
||||
+ }
|
||||
+
|
||||
+ /* Compute an address that should be within buf_ro. Complain if not. */
|
||||
+ addr = ((unsigned long long) buf_ro + pagesize) & ~(pagesize - 1);
|
||||
+
|
||||
+ if (addr <= (unsigned long long) buf_ro
|
||||
+ || addr >= (unsigned long long) buf_ro + sizeof (buf_ro))
|
||||
+ {
|
||||
+ fprintf (stderr, "Unable to compute a suitable address within buf_ro.\n");
|
||||
+ exit (1);
|
||||
+ }
|
||||
+
|
||||
+ mbuf_ro = mmap ((void *) addr, pagesize, PROT_READ,
|
||||
+ MAP_ANONYMOUS | MAP_PRIVATE | MAP_FIXED, -1, 0);
|
||||
+
|
||||
+ if (mbuf_ro == MAP_FAILED)
|
||||
+ {
|
||||
+ fprintf (stderr, "mmap #1 failed: %s.\n", strerror (errno));
|
||||
+ exit (1);
|
||||
+ }
|
||||
+
|
||||
+ /* Write (and fill) the R/W region. */
|
||||
+ for (i = 0; i < sizeof (buf_rw); i++)
|
||||
+ buf_rw[i] = 0x6b;
|
||||
+
|
||||
+ /* Compute an mmap address within buf_rw. Complain if it's somewhere
|
||||
+ else. */
|
||||
+ addr = ((unsigned long long) buf_rw + pagesize) & ~(pagesize - 1);
|
||||
+
|
||||
+ if (addr <= (unsigned long long) buf_rw
|
||||
+ || addr >= (unsigned long long) buf_rw + sizeof (buf_rw))
|
||||
+ {
|
||||
+ fprintf (stderr, "Unable to compute a suitable address within buf_rw.\n");
|
||||
+ exit (1);
|
||||
+ }
|
||||
+
|
||||
+ mbuf_rw = mmap ((void *) addr, pagesize, PROT_READ,
|
||||
+ MAP_ANONYMOUS | MAP_PRIVATE | MAP_FIXED, -1, 0);
|
||||
+
|
||||
+ if (mbuf_rw == MAP_FAILED)
|
||||
+ {
|
||||
+ fprintf (stderr, "mmap #2 failed: %s.\n", strerror (errno));
|
||||
+ exit (1);
|
||||
+ }
|
||||
+
|
||||
+ /* With correct ulimit, etc. this should cause a core dump. */
|
||||
+ abort ();
|
||||
+}
|
30
SOURCES/gdb-rhbz1842691-corefile-mem-access-15of15.patch
Normal file
30
SOURCES/gdb-rhbz1842691-corefile-mem-access-15of15.patch
Normal file
@ -0,0 +1,30 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Tue, 28 Jul 2020 09:49:56 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-15of15.patch
|
||||
|
||||
;; Add period to help text for maint print core-file-backed-mappings
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Thu Jul 23 13:26:44 2020 -0700
|
||||
|
||||
Fix BZ 26294 - Add period to help text for maint print core-file-backed-mappings
|
||||
|
||||
gdb/ChangeLog:
|
||||
|
||||
PR corefiles/26294
|
||||
* corelow.c (_initialize_corelow): Add period to help text
|
||||
for "maintenance print core-file-backed-mappings".
|
||||
|
||||
diff --git a/gdb/corelow.c b/gdb/corelow.c
|
||||
--- a/gdb/corelow.c
|
||||
+++ b/gdb/corelow.c
|
||||
@@ -1267,6 +1267,6 @@ Show whether CORE-FILE loads the build-id associated files automatically."),
|
||||
&setlist, &showlist);
|
||||
add_cmd ("core-file-backed-mappings", class_maintenance,
|
||||
maintenance_print_core_file_backed_mappings,
|
||||
- _("Print core file's file-backed mappings"),
|
||||
+ _("Print core file's file-backed mappings."),
|
||||
&maintenanceprintlist);
|
||||
}
|
60
SOURCES/gdb-rhbz1842691-corefile-mem-access-1of15.patch
Normal file
60
SOURCES/gdb-rhbz1842691-corefile-mem-access-1of15.patch
Normal file
@ -0,0 +1,60 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 27 Jul 2020 16:34:37 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-1of15.patch
|
||||
|
||||
;; Remove hack for GDB which sets the section size to 0
|
||||
;; Kevin Buettner, RH BZ 1842691
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
|
||||
Remove hack for GDB which sets the section size to 0
|
||||
|
||||
This commit removes a hack for GDB which was introduced in 2007.
|
||||
See:
|
||||
|
||||
https://sourceware.org/ml/binutils/2007-08/msg00044.html
|
||||
|
||||
That hack mostly allowed GDB's handling of core files to continue to
|
||||
work without any changes to GDB.
|
||||
|
||||
The problem with setting the section size to zero is that GDB won't
|
||||
know how big that section is/was. Often, this doesn't matter because
|
||||
the data in question are found in the exec file. But it can happen
|
||||
that the section describes memory that had been allocated, but never
|
||||
written to. In this instance, the contents of that memory region are
|
||||
not written to the core file. Also, since the region in question was
|
||||
dynamically allocated, it won't appear in the exec file. We don't
|
||||
want these regions to appear as inaccessible to GDB (since they *were*
|
||||
accessible when the process was live), so it's important that GDB know
|
||||
the size of the region.
|
||||
|
||||
I've made changes to GDB which correctly handles this case. When
|
||||
attempting to access memory, GDB will first consider core file data
|
||||
for which both SEC_ALLOC and SEC_HAS_CONTENTS is set. Next, if that
|
||||
fails, GDB will attempt to find the data in the exec file. Finally,
|
||||
if that also fails, GDB will attempt to access memory in the sections
|
||||
which are flagged as SEC_ALLOC, but not SEC_HAS_CONTENTS.
|
||||
|
||||
bfd/ChangeLog:
|
||||
|
||||
* elf.c (_bfd_elf_make_section_from_phdr): Remove hack for GDB.
|
||||
|
||||
diff --git a/bfd/elf.c b/bfd/elf.c
|
||||
--- a/bfd/elf.c
|
||||
+++ b/bfd/elf.c
|
||||
@@ -3032,14 +3032,6 @@ _bfd_elf_make_section_from_phdr (bfd *abfd,
|
||||
newsect->alignment_power = bfd_log2 (align);
|
||||
if (hdr->p_type == PT_LOAD)
|
||||
{
|
||||
- /* Hack for gdb. Segments that have not been modified do
|
||||
- not have their contents written to a core file, on the
|
||||
- assumption that a debugger can find the contents in the
|
||||
- executable. We flag this case by setting the fake
|
||||
- section size to zero. Note that "real" bss sections will
|
||||
- always have their contents dumped to the core file. */
|
||||
- if (bfd_get_format (abfd) == bfd_core)
|
||||
- newsect->size = 0;
|
||||
newsect->flags |= SEC_ALLOC;
|
||||
if (hdr->p_flags & PF_X)
|
||||
newsect->flags |= SEC_CODE;
|
129
SOURCES/gdb-rhbz1842691-corefile-mem-access-2of15.patch
Normal file
129
SOURCES/gdb-rhbz1842691-corefile-mem-access-2of15.patch
Normal file
@ -0,0 +1,129 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 27 Jul 2020 16:47:19 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-2of15.patch
|
||||
|
||||
;; Adjust corefile.exp test to show regression after bfd hack removal
|
||||
;; Kevin Buettner, RH BZ 1842691
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Tue May 12 17:44:19 2020 -0700
|
||||
|
||||
Adjust corefile.exp test to show regression after bfd hack removal
|
||||
|
||||
In his review of my BZ 25631 patch series, Pedro was unable to
|
||||
reproduce the regression which should occur after patch #1, "Remove
|
||||
hack for GDB which sets the section size to 0", is applied.
|
||||
|
||||
Pedro was using an ld version older than 2.30. Version 2.30
|
||||
introduced the linker option -z separate-code. Here's what the man
|
||||
page has to say about it:
|
||||
|
||||
Create separate code "PT_LOAD" segment header in the object. This
|
||||
specifies a memory segment that should contain only instructions
|
||||
and must be in wholly disjoint pages from any other data.
|
||||
|
||||
In ld version 2.31, use of separate-code became the default for
|
||||
Linux/x86. So, really, 2.31 or later is required in order to see the
|
||||
regression that occurs in recent Linux distributions when only the
|
||||
bfd hack removal patch is applied.
|
||||
|
||||
For the test case in question, use of the separate-code linker option
|
||||
means that the global variable "coremaker_ro" ends up in a separate
|
||||
load segment (though potentially with other read-only data). The
|
||||
upshot of this is that when only patch #1 is applied, GDB won't be
|
||||
able to correctly access coremaker_ro. The reason for this is due
|
||||
to the fact that this section will now have a non-zero size, but
|
||||
will not have contents from the core file to find this data.
|
||||
So GDB will ask BFD for the contents and BFD will respond with
|
||||
zeroes for anything from those sections. GDB should instead be
|
||||
looking in the executable for this data. Failing that, it can
|
||||
then ask BFD for a reasonable value. This is what a later patch
|
||||
in this series does.
|
||||
|
||||
When using ld versions earlier than 2.31 (or 2.30 w/ the
|
||||
-z separate-code option explicitly provided to the linker), there is
|
||||
the possibility that coremaker_ro ends up being placed near other data
|
||||
which is recorded in the core file. That means that the correct value
|
||||
will end up in the core file, simply because it resides on a page that
|
||||
the kernel chooses to put in the core file. This is why Pedro wasn't
|
||||
able to reproduce the regression that should occur after fixing the
|
||||
BFD hack.
|
||||
|
||||
This patch places a big chunk of memory, two pages worth on x86, in
|
||||
front of "coremaker_ro" to attempt to force it onto another page
|
||||
without requiring use of that new-fangled linker switch.
|
||||
|
||||
Speaking of which, I considered changing the test to use
|
||||
-z separate-code, but this won't work because it didn't
|
||||
exist prior to version 2.30. The linker would probably complain
|
||||
of an unrecognized switch. Also, it likely won't be available in
|
||||
other linkers not based on current binutils. I.e. it probably won't
|
||||
work in FreeBSD, NetBSD, etc.
|
||||
|
||||
To make this more concrete, this is what *should* happen when
|
||||
attempting to access coremaker_ro when only patch #1 is applied:
|
||||
|
||||
Core was generated by `/mesquite2/sourceware-git/f28-coresegs/bld/gdb/testsuite/outputs/gdb.base/coref'.
|
||||
Program terminated with signal SIGABRT, Aborted.
|
||||
#0 0x00007f68205deefb in raise () from /lib64/libc.so.6
|
||||
(gdb) p coremaker_ro
|
||||
$1 = 0
|
||||
|
||||
Note that this result is wrong; 201 should have been printed instead.
|
||||
But that's the point of the rest of the patch series.
|
||||
|
||||
However, without this commit, or when using an old Linux distro with
|
||||
a pre-2.31 ld, this is what you might see instead:
|
||||
|
||||
Core was generated by `/mesquite2/sourceware-git/f28-coresegs/bld/gdb/testsuite/outputs/gdb.base/coref'.
|
||||
Program terminated with signal SIGABRT, Aborted.
|
||||
#0 0x00007f63dd658efb in raise () from /lib64/libc.so.6
|
||||
(gdb) p coremaker_ro
|
||||
$1 = 201
|
||||
|
||||
I.e. it prints the right answer, which sort of makes it seem like the
|
||||
rest of the series isn't required.
|
||||
|
||||
Now, back to the patch itself... what should be the size of the memory
|
||||
chunk placed before coremaker_ro?
|
||||
|
||||
It needs to be at least as big as the page size (PAGE_SIZE) from
|
||||
the kernel. For x86 and several other architectures this value is
|
||||
4096. I used MAPSIZE which is defined to be 8192 in coremaker.c.
|
||||
So it's twice as big as what's currently needed for most Linux
|
||||
architectures. The constant PAGE_SIZE is available from <sys/user.h>,
|
||||
but this isn't portable either. In the end, it seemed simpler to
|
||||
just pick a value and hope that it's big enough. (Running a separate
|
||||
program which finds the page size via sysconf(_SC_PAGESIZE) and then
|
||||
passes it to the compilation via a -D switch seemed like overkill
|
||||
for a case which is rendered moot by recent linker versions.)
|
||||
|
||||
Further information can be found here:
|
||||
|
||||
https://sourceware.org/pipermail/gdb-patches/2020-May/168168.html
|
||||
https://sourceware.org/pipermail/gdb-patches/2020-May/168170.html
|
||||
|
||||
Thanks to H.J. Lu for telling me about the '-z separate-code' linker
|
||||
switch.
|
||||
|
||||
gdb/testsuite/ChangeLog:
|
||||
|
||||
* gdb.base/coremaker.c (filler_ro): New global constant.
|
||||
|
||||
diff --git a/gdb/testsuite/gdb.base/coremaker.c b/gdb/testsuite/gdb.base/coremaker.c
|
||||
--- a/gdb/testsuite/gdb.base/coremaker.c
|
||||
+++ b/gdb/testsuite/gdb.base/coremaker.c
|
||||
@@ -42,6 +42,12 @@ char *buf2;
|
||||
int coremaker_data = 1; /* In Data section */
|
||||
int coremaker_bss; /* In BSS section */
|
||||
|
||||
+/* Place a chunk of memory before coremaker_ro to improve the chances
|
||||
+ that coremaker_ro will end up on it's own page. See:
|
||||
+
|
||||
+ https://sourceware.org/pipermail/gdb-patches/2020-May/168168.html
|
||||
+ https://sourceware.org/pipermail/gdb-patches/2020-May/168170.html */
|
||||
+const unsigned char filler_ro[MAPSIZE] = {1, 2, 3, 4, 5, 6, 7, 8};
|
||||
const int coremaker_ro = 201; /* In Read-Only Data section */
|
||||
|
||||
/* Note that if the mapping fails for any reason, we set buf2
|
174
SOURCES/gdb-rhbz1842691-corefile-mem-access-3of15.patch
Normal file
174
SOURCES/gdb-rhbz1842691-corefile-mem-access-3of15.patch
Normal file
@ -0,0 +1,174 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 27 Jul 2020 16:52:18 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-3of15.patch
|
||||
|
||||
;; section_table_xfer_memory: Replace section name with callback predicate
|
||||
;; Kevin Buettner, RH BZ 1842691
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Wed Mar 4 17:42:41 2020 -0700
|
||||
|
||||
section_table_xfer_memory: Replace section name with callback predicate
|
||||
|
||||
This patch is motivated by the need to be able to select sections
|
||||
that section_table_xfer_memory_partial should consider for memory
|
||||
transfers. I'll use this facility in the next patch in this series.
|
||||
|
||||
section_table_xfer_memory_partial() can currently be passed a section
|
||||
name which may be used to make name-based selections. This is similar
|
||||
to what I want to do, except that I want to be able to consider
|
||||
section flags instead of the name.
|
||||
|
||||
I'm replacing the section name parameter with a predicate that,
|
||||
when passed a pointer to a target_section struct, will return
|
||||
true if that section should be further considered, or false which
|
||||
indicates that it shouldn't.
|
||||
|
||||
I've converted the one existing use where a non-NULL section
|
||||
name is passed to section_table_xfer_memory_partial(). Instead
|
||||
of passing the section name, it now looks like this:
|
||||
|
||||
auto match_cb = [=] (const struct target_section *s)
|
||||
{
|
||||
return (strcmp (section_name, s->the_bfd_section->name) == 0);
|
||||
};
|
||||
|
||||
return section_table_xfer_memory_partial (readbuf, writebuf,
|
||||
memaddr, len, xfered_len,
|
||||
table->sections,
|
||||
table->sections_end,
|
||||
match_cb);
|
||||
|
||||
The other callers all passed NULL; they've been simplified somewhat
|
||||
in that they no longer need to pass NULL.
|
||||
|
||||
gdb/ChangeLog:
|
||||
|
||||
* exec.h (section_table_xfer_memory): Revise declaration,
|
||||
replacing section name parameter with an optional callback
|
||||
predicate.
|
||||
* exec.c (section_table_xfer_memory): Likewise.
|
||||
* bfd-target.c, exec.c, target.c, corelow.c: Adjust all callers
|
||||
of section_table_xfer_memory.
|
||||
|
||||
diff --git a/gdb/bfd-target.c b/gdb/bfd-target.c
|
||||
--- a/gdb/bfd-target.c
|
||||
+++ b/gdb/bfd-target.c
|
||||
@@ -77,8 +77,7 @@ target_bfd::xfer_partial (target_object object,
|
||||
return section_table_xfer_memory_partial (readbuf, writebuf,
|
||||
offset, len, xfered_len,
|
||||
m_table.sections,
|
||||
- m_table.sections_end,
|
||||
- NULL);
|
||||
+ m_table.sections_end);
|
||||
}
|
||||
default:
|
||||
return TARGET_XFER_E_IO;
|
||||
diff --git a/gdb/corelow.c b/gdb/corelow.c
|
||||
--- a/gdb/corelow.c
|
||||
+++ b/gdb/corelow.c
|
||||
@@ -758,8 +758,7 @@ core_target::xfer_partial (enum target_object object, const char *annex,
|
||||
(readbuf, writebuf,
|
||||
offset, len, xfered_len,
|
||||
m_core_section_table.sections,
|
||||
- m_core_section_table.sections_end,
|
||||
- NULL));
|
||||
+ m_core_section_table.sections_end));
|
||||
|
||||
case TARGET_OBJECT_AUXV:
|
||||
if (readbuf)
|
||||
diff --git a/gdb/exec.c b/gdb/exec.c
|
||||
--- a/gdb/exec.c
|
||||
+++ b/gdb/exec.c
|
||||
@@ -792,7 +792,8 @@ section_table_xfer_memory_partial (gdb_byte *readbuf, const gdb_byte *writebuf,
|
||||
ULONGEST *xfered_len,
|
||||
struct target_section *sections,
|
||||
struct target_section *sections_end,
|
||||
- const char *section_name)
|
||||
+ gdb::function_view<bool
|
||||
+ (const struct target_section *)> match_cb)
|
||||
{
|
||||
int res;
|
||||
struct target_section *p;
|
||||
@@ -808,7 +809,7 @@ section_table_xfer_memory_partial (gdb_byte *readbuf, const gdb_byte *writebuf,
|
||||
struct bfd_section *asect = p->the_bfd_section;
|
||||
bfd *abfd = asect->owner;
|
||||
|
||||
- if (section_name && strcmp (section_name, asect->name) != 0)
|
||||
+ if (match_cb != nullptr && !match_cb (p))
|
||||
continue; /* not the section we need. */
|
||||
if (memaddr >= p->addr)
|
||||
{
|
||||
@@ -881,8 +882,7 @@ exec_target::xfer_partial (enum target_object object,
|
||||
return section_table_xfer_memory_partial (readbuf, writebuf,
|
||||
offset, len, xfered_len,
|
||||
table->sections,
|
||||
- table->sections_end,
|
||||
- NULL);
|
||||
+ table->sections_end);
|
||||
else
|
||||
return TARGET_XFER_E_IO;
|
||||
}
|
||||
diff --git a/gdb/exec.h b/gdb/exec.h
|
||||
--- a/gdb/exec.h
|
||||
+++ b/gdb/exec.h
|
||||
@@ -58,8 +58,13 @@ extern enum target_xfer_status
|
||||
Request to transfer up to LEN 8-bit bytes of the target sections
|
||||
defined by SECTIONS and SECTIONS_END. The OFFSET specifies the
|
||||
starting address.
|
||||
- If SECTION_NAME is not NULL, only access sections with that same
|
||||
- name.
|
||||
+
|
||||
+ The MATCH_CB predicate is optional; when provided it will be called
|
||||
+ for each section under consideration. When MATCH_CB evaluates as
|
||||
+ true, the section remains under consideration; a false result
|
||||
+ removes it from consideration for performing the memory transfers
|
||||
+ noted above. See memory_xfer_partial_1() in target.c for an
|
||||
+ example.
|
||||
|
||||
Return the number of bytes actually transfered, or zero when no
|
||||
data is available for the requested range.
|
||||
@@ -76,7 +81,9 @@ extern enum target_xfer_status
|
||||
ULONGEST, ULONGEST, ULONGEST *,
|
||||
struct target_section *,
|
||||
struct target_section *,
|
||||
- const char *);
|
||||
+ gdb::function_view<bool
|
||||
+ (const struct target_section *)> match_cb
|
||||
+ = nullptr);
|
||||
|
||||
/* Read from mappable read-only sections of BFD executable files.
|
||||
Similar to exec_read_partial_read_only, but return
|
||||
diff --git a/gdb/target.c b/gdb/target.c
|
||||
--- a/gdb/target.c
|
||||
+++ b/gdb/target.c
|
||||
@@ -1022,11 +1022,17 @@ memory_xfer_partial_1 (struct target_ops *ops, enum target_object object,
|
||||
const char *section_name = section->the_bfd_section->name;
|
||||
|
||||
memaddr = overlay_mapped_address (memaddr, section);
|
||||
+
|
||||
+ auto match_cb = [=] (const struct target_section *s)
|
||||
+ {
|
||||
+ return (strcmp (section_name, s->the_bfd_section->name) == 0);
|
||||
+ };
|
||||
+
|
||||
return section_table_xfer_memory_partial (readbuf, writebuf,
|
||||
memaddr, len, xfered_len,
|
||||
table->sections,
|
||||
table->sections_end,
|
||||
- section_name);
|
||||
+ match_cb);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1044,8 +1050,7 @@ memory_xfer_partial_1 (struct target_ops *ops, enum target_object object,
|
||||
return section_table_xfer_memory_partial (readbuf, writebuf,
|
||||
memaddr, len, xfered_len,
|
||||
table->sections,
|
||||
- table->sections_end,
|
||||
- NULL);
|
||||
+ table->sections_end);
|
||||
}
|
||||
}
|
||||
|
236
SOURCES/gdb-rhbz1842691-corefile-mem-access-4of15.patch
Normal file
236
SOURCES/gdb-rhbz1842691-corefile-mem-access-4of15.patch
Normal file
@ -0,0 +1,236 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 27 Jul 2020 17:11:49 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-4of15.patch
|
||||
|
||||
;; Provide access to non SEC_HAS_CONTENTS core file sections
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Wed Mar 4 17:42:42 2020 -0700
|
||||
|
||||
Provide access to non SEC_HAS_CONTENTS core file sections
|
||||
|
||||
Consider the following program:
|
||||
|
||||
- - - mkmmapcore.c - - -
|
||||
|
||||
static char *buf;
|
||||
|
||||
int
|
||||
main (int argc, char **argv)
|
||||
{
|
||||
buf = mmap (NULL, 8192, PROT_READ | PROT_WRITE,
|
||||
MAP_ANONYMOUS | MAP_PRIVATE, -1, 0);
|
||||
abort ();
|
||||
}
|
||||
- - - end mkmmapcore.c - - -
|
||||
|
||||
Compile it like this:
|
||||
|
||||
gcc -g -o mkmmapcore mkmmapcore.c
|
||||
|
||||
Now let's run it from GDB. I've already placed a breakpoint on the
|
||||
line with the abort() call and have run to that breakpoint.
|
||||
|
||||
Breakpoint 1, main (argc=1, argv=0x7fffffffd678) at mkmmapcore.c:11
|
||||
11 abort ();
|
||||
(gdb) x/x buf
|
||||
0x7ffff7fcb000: 0x00000000
|
||||
|
||||
Note that we can examine the memory allocated via the call to mmap().
|
||||
|
||||
Now let's try debugging a core file created by running this program.
|
||||
Depending on your system, in order to make a core file, you may have to
|
||||
run the following as root (or using sudo):
|
||||
|
||||
echo core > /proc/sys/kernel/core_pattern
|
||||
|
||||
It may also be necessary to do:
|
||||
|
||||
ulimit -c unlimited
|
||||
|
||||
I'm using Fedora 31. YMMV if you're using one of the BSDs or some other
|
||||
(non-Linux) system.
|
||||
|
||||
This is what things look like when we debug the core file:
|
||||
|
||||
[kev@f31-1 tmp]$ gdb -q ./mkmmapcore core.304767
|
||||
Reading symbols from ./mkmmapcore...
|
||||
[New LWP 304767]
|
||||
Core was generated by `/tmp/mkmmapcore'.
|
||||
Program terminated with signal SIGABRT, Aborted.
|
||||
#0 __GI_raise (sig=sig@entry=6) at ../sysdeps/unix/sysv/linux/raise.c:50
|
||||
50 return ret;
|
||||
(gdb) x/x buf
|
||||
0x7ffff7fcb000: Cannot access memory at address 0x7ffff7fcb000
|
||||
|
||||
Note that we can no longer access the memory region allocated by mmap().
|
||||
|
||||
Back in 2007, a hack for GDB was added to _bfd_elf_make_section_from_phdr()
|
||||
in bfd/elf.c:
|
||||
|
||||
/* Hack for gdb. Segments that have not been modified do
|
||||
not have their contents written to a core file, on the
|
||||
assumption that a debugger can find the contents in the
|
||||
executable. We flag this case by setting the fake
|
||||
section size to zero. Note that "real" bss sections will
|
||||
always have their contents dumped to the core file. */
|
||||
if (bfd_get_format (abfd) == bfd_core)
|
||||
newsect->size = 0;
|
||||
|
||||
You can find the entire patch plus links to other discussion starting
|
||||
here:
|
||||
|
||||
https://sourceware.org/ml/binutils/2007-08/msg00047.html
|
||||
|
||||
This hack sets the size of certain BFD sections to 0, which
|
||||
effectively causes GDB to ignore them. I think it's likely that the
|
||||
bug described above existed even before this hack was added, but I
|
||||
have no easy way to test this now.
|
||||
|
||||
The output from objdump -h shows the result of this hack:
|
||||
|
||||
25 load13 00000000 00007ffff7fcb000 0000000000000000 00013000 2**12
|
||||
ALLOC
|
||||
|
||||
(The first field, after load13, shows the size of 0.)
|
||||
|
||||
Once the hack is removed, the output from objdump -h shows the correct
|
||||
size:
|
||||
|
||||
25 load13 00002000 00007ffff7fcb000 0000000000000000 00013000 2**12
|
||||
ALLOC
|
||||
|
||||
(This is a digression, but I think it's good that objdump will now show
|
||||
the correct size.)
|
||||
|
||||
If we remove the hack from bfd/elf.c, but do nothing to GDB, we'll
|
||||
see the following regression:
|
||||
|
||||
FAIL: gdb.base/corefile.exp: print coremaker_ro
|
||||
|
||||
The reason for this is that all sections which have the BFD flag
|
||||
SEC_ALLOC set, but for which SEC_HAS_CONTENTS is not set no longer
|
||||
have zero size. Some of these sections have data that can (and should)
|
||||
be read from the executable. (Sections for which SEC_HAS_CONTENTS
|
||||
is set should be read from the core file; sections which do not have
|
||||
this flag set need to either be read from the executable or, failing
|
||||
that, from the core file using whatever BFD decides is the best value
|
||||
to present to the user - it uses zeros.)
|
||||
|
||||
At present, due to the way that the target strata are traversed when
|
||||
attempting to access memory, the non-SEC_HAS_CONTENTS sections will be
|
||||
read as zeroes from the process_stratum (which in this case is the
|
||||
core file stratum) without first checking the file stratum, which is
|
||||
where the data might actually be found.
|
||||
|
||||
What we should be doing is this:
|
||||
|
||||
- Attempt to access core file data for SEC_HAS_CONTENTS sections.
|
||||
- Attempt to access executable file data if the above fails.
|
||||
- Attempt to access core file data for non SEC_HAS_CONTENTS sections, if
|
||||
both of the above fail.
|
||||
|
||||
This corresponds to the analysis of Daniel Jacobowitz back in 2007
|
||||
when the hack was added to BFD:
|
||||
|
||||
https://sourceware.org/legacy-ml/binutils/2007-08/msg00045.html
|
||||
|
||||
The difference, observed by Pedro in his review of my v1 patches, is
|
||||
that I'm using "the section flags as proxy for the p_filesz/p_memsz
|
||||
checks."
|
||||
|
||||
gdb/ChangeLog:
|
||||
|
||||
PR corefiles/25631
|
||||
* corelow.c (core_target:xfer_partial): Revise
|
||||
TARGET_OBJECT_MEMORY case to consider non-SEC_HAS_CONTENTS
|
||||
case after first checking the stratum beneath the core
|
||||
target.
|
||||
(has_all_memory): Return true.
|
||||
* target.c (raw_memory_xfer_partial): Revise comment
|
||||
regarding use of has_all_memory.
|
||||
|
||||
diff --git a/gdb/corelow.c b/gdb/corelow.c
|
||||
--- a/gdb/corelow.c
|
||||
+++ b/gdb/corelow.c
|
||||
@@ -93,7 +93,7 @@ public:
|
||||
|
||||
const char *thread_name (struct thread_info *) override;
|
||||
|
||||
- bool has_all_memory () override { return false; }
|
||||
+ bool has_all_memory () override { return true; }
|
||||
bool has_memory () override;
|
||||
bool has_stack () override;
|
||||
bool has_registers () override;
|
||||
@@ -754,12 +754,47 @@ core_target::xfer_partial (enum target_object object, const char *annex,
|
||||
switch (object)
|
||||
{
|
||||
case TARGET_OBJECT_MEMORY:
|
||||
- return (section_table_xfer_memory_partial
|
||||
- (readbuf, writebuf,
|
||||
- offset, len, xfered_len,
|
||||
- m_core_section_table.sections,
|
||||
- m_core_section_table.sections_end));
|
||||
+ {
|
||||
+ enum target_xfer_status xfer_status;
|
||||
+
|
||||
+ /* Try accessing memory contents from core file data,
|
||||
+ restricting consideration to those sections for which
|
||||
+ the BFD section flag SEC_HAS_CONTENTS is set. */
|
||||
+ auto has_contents_cb = [] (const struct target_section *s)
|
||||
+ {
|
||||
+ return ((s->the_bfd_section->flags & SEC_HAS_CONTENTS) != 0);
|
||||
+ };
|
||||
+ xfer_status = section_table_xfer_memory_partial
|
||||
+ (readbuf, writebuf,
|
||||
+ offset, len, xfered_len,
|
||||
+ m_core_section_table.sections,
|
||||
+ m_core_section_table.sections_end,
|
||||
+ has_contents_cb);
|
||||
+ if (xfer_status == TARGET_XFER_OK)
|
||||
+ return TARGET_XFER_OK;
|
||||
+
|
||||
+ /* Now check the stratum beneath us; this should be file_stratum. */
|
||||
+ xfer_status = this->beneath ()->xfer_partial (object, annex, readbuf,
|
||||
+ writebuf, offset, len,
|
||||
+ xfered_len);
|
||||
+ if (xfer_status == TARGET_XFER_OK)
|
||||
+ return TARGET_XFER_OK;
|
||||
|
||||
+ /* Finally, attempt to access data in core file sections with
|
||||
+ no contents. These will typically read as all zero. */
|
||||
+ auto no_contents_cb = [&] (const struct target_section *s)
|
||||
+ {
|
||||
+ return !has_contents_cb (s);
|
||||
+ };
|
||||
+ xfer_status = section_table_xfer_memory_partial
|
||||
+ (readbuf, writebuf,
|
||||
+ offset, len, xfered_len,
|
||||
+ m_core_section_table.sections,
|
||||
+ m_core_section_table.sections_end,
|
||||
+ no_contents_cb);
|
||||
+
|
||||
+ return xfer_status;
|
||||
+ }
|
||||
case TARGET_OBJECT_AUXV:
|
||||
if (readbuf)
|
||||
{
|
||||
diff --git a/gdb/target.c b/gdb/target.c
|
||||
--- a/gdb/target.c
|
||||
+++ b/gdb/target.c
|
||||
@@ -967,8 +967,11 @@ raw_memory_xfer_partial (struct target_ops *ops, gdb_byte *readbuf,
|
||||
if (res == TARGET_XFER_UNAVAILABLE)
|
||||
break;
|
||||
|
||||
- /* We want to continue past core files to executables, but not
|
||||
- past a running target's memory. */
|
||||
+ /* Don't continue past targets which have all the memory.
|
||||
+ At one time, this code was necessary to read data from
|
||||
+ executables / shared libraries when data for the requested
|
||||
+ addresses weren't available in the core file. But now the
|
||||
+ core target handles this case itself. */
|
||||
if (ops->has_all_memory ())
|
||||
break;
|
||||
|
68
SOURCES/gdb-rhbz1842691-corefile-mem-access-5of15.patch
Normal file
68
SOURCES/gdb-rhbz1842691-corefile-mem-access-5of15.patch
Normal file
@ -0,0 +1,68 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 27 Jul 2020 17:27:39 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-5of15.patch
|
||||
|
||||
;; Test ability to access unwritten-to mmap data in core file
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Wed Mar 4 17:42:43 2020 -0700
|
||||
|
||||
Test ability to access unwritten-to mmap data in core file
|
||||
|
||||
gdb/testsuite/ChangeLog:
|
||||
|
||||
PR corefiles/25631
|
||||
* gdb.base/corefile.exp (accessing anonymous, unwritten-to mmap data):
|
||||
New test.
|
||||
* gdb.base/coremaker.c (buf3): New global.
|
||||
(mmapdata): Add mmap call which uses MAP_ANONYMOUS and MAP_PRIVATE
|
||||
flags.
|
||||
|
||||
diff --git a/gdb/testsuite/gdb.base/corefile.exp b/gdb/testsuite/gdb.base/corefile.exp
|
||||
--- a/gdb/testsuite/gdb.base/corefile.exp
|
||||
+++ b/gdb/testsuite/gdb.base/corefile.exp
|
||||
@@ -175,6 +175,15 @@ gdb_test_multiple "x/8bd buf2" "$test" {
|
||||
}
|
||||
}
|
||||
|
||||
+# Test ability to read anonymous and, more importantly, unwritten-to
|
||||
+# mmap'd data.
|
||||
+
|
||||
+if { ![istarget *-linux*] } {
|
||||
+ setup_xfail "*-*-*"
|
||||
+}
|
||||
+gdb_test "x/wx buf3" "$hex:\[ \t\]+0x00000000" \
|
||||
+ "accessing anonymous, unwritten-to mmap data"
|
||||
+
|
||||
# test reinit_frame_cache
|
||||
|
||||
gdb_load ${binfile}
|
||||
diff --git a/gdb/testsuite/gdb.base/coremaker.c b/gdb/testsuite/gdb.base/coremaker.c
|
||||
--- a/gdb/testsuite/gdb.base/coremaker.c
|
||||
+++ b/gdb/testsuite/gdb.base/coremaker.c
|
||||
@@ -38,6 +38,7 @@
|
||||
|
||||
char *buf1;
|
||||
char *buf2;
|
||||
+char *buf3;
|
||||
|
||||
int coremaker_data = 1; /* In Data section */
|
||||
int coremaker_bss; /* In BSS section */
|
||||
@@ -104,6 +105,15 @@ mmapdata ()
|
||||
}
|
||||
/* Touch buf2 so kernel writes it out into 'core'. */
|
||||
buf2[0] = buf1[0];
|
||||
+
|
||||
+ /* Create yet another region which is allocated, but not written to. */
|
||||
+ buf3 = mmap (NULL, MAPSIZE, PROT_READ | PROT_WRITE,
|
||||
+ MAP_ANONYMOUS | MAP_PRIVATE, -1, 0);
|
||||
+ if (buf3 == (char *) -1)
|
||||
+ {
|
||||
+ perror ("mmap failed");
|
||||
+ return;
|
||||
+ }
|
||||
}
|
||||
|
||||
void
|
62
SOURCES/gdb-rhbz1842691-corefile-mem-access-6of15.patch
Normal file
62
SOURCES/gdb-rhbz1842691-corefile-mem-access-6of15.patch
Normal file
@ -0,0 +1,62 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 27 Jul 2020 17:32:50 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-6of15.patch
|
||||
|
||||
;; Update binary_get_section_contents to seek using section's file position
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Thu Jun 11 18:58:49 2020 -0700
|
||||
|
||||
Update binary_get_section_contents to seek using section's file position
|
||||
|
||||
I have a patch for GDB which opens and reads from BFDs using the
|
||||
"binary" target. However, for it to work, we need to be able to get a
|
||||
section's contents based from the file position of that section.
|
||||
|
||||
At the moment, reading a section's contents will always read from the
|
||||
start of the file regardless of where that section is located. While
|
||||
this was fine for the original use of the "binary" target, it won't
|
||||
work for my use case. This change shouldn't impact any existing
|
||||
callers due to the fact that the single .data section is initialized
|
||||
with a filepos of 0.
|
||||
|
||||
bfd/ChangeLog:
|
||||
|
||||
* binary.c (binary_get_section_contents): Seek using offset
|
||||
from section's file position.
|
||||
|
||||
diff --git a/bfd/binary.c b/bfd/binary.c
|
||||
--- a/bfd/binary.c
|
||||
+++ b/bfd/binary.c
|
||||
@@ -19,10 +19,10 @@
|
||||
Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
|
||||
MA 02110-1301, USA. */
|
||||
|
||||
-/* This is a BFD backend which may be used to write binary objects.
|
||||
- It may only be used for output, not input. The intention is that
|
||||
- this may be used as an output format for objcopy in order to
|
||||
- generate raw binary data.
|
||||
+/* This is a BFD backend which may be used to read or write binary
|
||||
+ objects. Historically, it was used as an output format for objcopy
|
||||
+ in order to generate raw binary data, but is now used for other
|
||||
+ purposes as well.
|
||||
|
||||
This is very simple. The only complication is that the real data
|
||||
will start at some address X, and in some cases we will not want to
|
||||
@@ -97,12 +97,12 @@ binary_object_p (bfd *abfd)
|
||||
|
||||
static bfd_boolean
|
||||
binary_get_section_contents (bfd *abfd,
|
||||
- asection *section ATTRIBUTE_UNUSED,
|
||||
+ asection *section,
|
||||
void * location,
|
||||
file_ptr offset,
|
||||
bfd_size_type count)
|
||||
{
|
||||
- if (bfd_seek (abfd, offset, SEEK_SET) != 0
|
||||
+ if (bfd_seek (abfd, section->filepos + offset, SEEK_SET) != 0
|
||||
|| bfd_bread (location, count, abfd) != count)
|
||||
return FALSE;
|
||||
return TRUE;
|
180
SOURCES/gdb-rhbz1842691-corefile-mem-access-7of15.patch
Normal file
180
SOURCES/gdb-rhbz1842691-corefile-mem-access-7of15.patch
Normal file
@ -0,0 +1,180 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 27 Jul 2020 18:01:32 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-7of15.patch
|
||||
|
||||
;; Add new gdbarch method, read_core_file_mappings
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Fri Jul 3 13:32:08 2020 -0700
|
||||
|
||||
Add new gdbarch method, read_core_file_mappings
|
||||
|
||||
The new gdbarch method, read_core_file_mappings, will be used for
|
||||
reading file-backed mappings from a core file. It'll be used
|
||||
for two purposes: 1) to construct a table of file-backed mappings
|
||||
in corelow.c, and 2) for display of core file mappings.
|
||||
|
||||
For Linux, I tried a different approach in which knowledge of the note
|
||||
format was placed directly in corelow.c. This seemed okay at first;
|
||||
it was only one note format and the note format was fairly simple.
|
||||
After looking at FreeBSD's note/mapping reading code, I concluded
|
||||
that it's best to leave architecture specific details for decoding
|
||||
the note in (architecture specific) tdep files.
|
||||
|
||||
With regard to display of core file mappings, I experimented with
|
||||
placing the mappings display code in corelow.c. It has access to the
|
||||
file-backed mappings which were read in when the core file was loaded.
|
||||
And, better, still common code could be used for all architectures.
|
||||
But, again, the FreeBSD mapping code convinced me that this was not
|
||||
the best approach since it has even more mapping info than Linux.
|
||||
Display code which would work well for Linux will leave out mappings
|
||||
as well as protection info for mappings.
|
||||
|
||||
So, for these reasons, I'm introducing a new gdbarch method for
|
||||
reading core file mappings.
|
||||
|
||||
gdb/ChangeLog:
|
||||
|
||||
* arch-utils.c (default_read_core_file_mappings): New function.
|
||||
* arch-utils.c (default_read_core_file_mappings): Declare.
|
||||
* gdbarch.sh (read_core_file_mappings): New gdbarch method.
|
||||
* gdbarch.h, gdbarch.c: Regenerate.
|
||||
|
||||
diff --git a/gdb/arch-utils.c b/gdb/arch-utils.c
|
||||
--- a/gdb/arch-utils.c
|
||||
+++ b/gdb/arch-utils.c
|
||||
@@ -1004,6 +1004,22 @@ default_get_pc_address_flags (frame_info *frame, CORE_ADDR pc)
|
||||
return "";
|
||||
}
|
||||
|
||||
+/* See arch-utils.h. */
|
||||
+void
|
||||
+default_read_core_file_mappings (struct gdbarch *gdbarch,
|
||||
+ struct bfd *cbfd,
|
||||
+ gdb::function_view<void (ULONGEST count)>
|
||||
+ pre_loop_cb,
|
||||
+ gdb::function_view<void (int num,
|
||||
+ ULONGEST start,
|
||||
+ ULONGEST end,
|
||||
+ ULONGEST file_ofs,
|
||||
+ const char *filename,
|
||||
+ const void *other)>
|
||||
+ loop_cb)
|
||||
+{
|
||||
+}
|
||||
+
|
||||
void
|
||||
_initialize_gdbarch_utils (void)
|
||||
{
|
||||
diff --git a/gdb/arch-utils.h b/gdb/arch-utils.h
|
||||
--- a/gdb/arch-utils.h
|
||||
+++ b/gdb/arch-utils.h
|
||||
@@ -276,4 +276,16 @@ extern ULONGEST default_type_align (struct gdbarch *gdbarch,
|
||||
extern std::string default_get_pc_address_flags (frame_info *frame,
|
||||
CORE_ADDR pc);
|
||||
|
||||
+/* Default implementation of gdbarch read_core_file_mappings method. */
|
||||
+extern void default_read_core_file_mappings (struct gdbarch *gdbarch,
|
||||
+ struct bfd *cbfd,
|
||||
+ gdb::function_view<void (ULONGEST count)>
|
||||
+ pre_loop_cb,
|
||||
+ gdb::function_view<void (int num,
|
||||
+ ULONGEST start,
|
||||
+ ULONGEST end,
|
||||
+ ULONGEST file_ofs,
|
||||
+ const char *filename,
|
||||
+ const void *other)>
|
||||
+ loop_cb);
|
||||
#endif /* ARCH_UTILS_H */
|
||||
diff --git a/gdb/gdbarch.c b/gdb/gdbarch.c
|
||||
--- a/gdb/gdbarch.c
|
||||
+++ b/gdb/gdbarch.c
|
||||
@@ -358,6 +358,7 @@ struct gdbarch
|
||||
const disasm_options_and_args_t * valid_disassembler_options;
|
||||
gdbarch_type_align_ftype *type_align;
|
||||
gdbarch_get_pc_address_flags_ftype *get_pc_address_flags;
|
||||
+ gdbarch_read_core_file_mappings_ftype *read_core_file_mappings;
|
||||
};
|
||||
|
||||
/* Create a new ``struct gdbarch'' based on information provided by
|
||||
@@ -473,6 +474,7 @@ gdbarch_alloc (const struct gdbarch_info *info,
|
||||
gdbarch->addressable_memory_unit_size = default_addressable_memory_unit_size;
|
||||
gdbarch->type_align = default_type_align;
|
||||
gdbarch->get_pc_address_flags = default_get_pc_address_flags;
|
||||
+ gdbarch->read_core_file_mappings = default_read_core_file_mappings;
|
||||
/* gdbarch_alloc() */
|
||||
|
||||
return gdbarch;
|
||||
@@ -721,6 +723,7 @@ verify_gdbarch (struct gdbarch *gdbarch)
|
||||
/* Skip verify of valid_disassembler_options, invalid_p == 0 */
|
||||
/* Skip verify of type_align, invalid_p == 0 */
|
||||
/* Skip verify of get_pc_address_flags, invalid_p == 0 */
|
||||
+ /* Skip verify of read_core_file_mappings, invalid_p == 0 */
|
||||
if (!log.empty ())
|
||||
internal_error (__FILE__, __LINE__,
|
||||
_("verify_gdbarch: the following are invalid ...%s"),
|
||||
@@ -1287,6 +1290,9 @@ gdbarch_dump (struct gdbarch *gdbarch, struct ui_file *file)
|
||||
fprintf_unfiltered (file,
|
||||
"gdbarch_dump: ravenscar_ops = %s\n",
|
||||
host_address_to_string (gdbarch->ravenscar_ops));
|
||||
+ fprintf_unfiltered (file,
|
||||
+ "gdbarch_dump: read_core_file_mappings = <%s>\n",
|
||||
+ host_address_to_string (gdbarch->read_core_file_mappings));
|
||||
fprintf_unfiltered (file,
|
||||
"gdbarch_dump: gdbarch_read_pc_p() = %d\n",
|
||||
gdbarch_read_pc_p (gdbarch));
|
||||
@@ -5156,6 +5162,23 @@ set_gdbarch_get_pc_address_flags (struct gdbarch *gdbarch,
|
||||
gdbarch->get_pc_address_flags = get_pc_address_flags;
|
||||
}
|
||||
|
||||
+void
|
||||
+gdbarch_read_core_file_mappings (struct gdbarch *gdbarch, struct bfd *cbfd,gdb::function_view<void (ULONGEST count)> pre_loop_cb,gdb::function_view<void (int num, ULONGEST start, ULONGEST end, ULONGEST file_ofs, const char *filename, const void *other)> loop_cb)
|
||||
+{
|
||||
+ gdb_assert (gdbarch != NULL);
|
||||
+ gdb_assert (gdbarch->read_core_file_mappings != NULL);
|
||||
+ if (gdbarch_debug >= 2)
|
||||
+ fprintf_unfiltered (gdb_stdlog, "gdbarch_read_core_file_mappings called\n");
|
||||
+ gdbarch->read_core_file_mappings (gdbarch, cbfd, pre_loop_cb, loop_cb);
|
||||
+}
|
||||
+
|
||||
+void
|
||||
+set_gdbarch_read_core_file_mappings (struct gdbarch *gdbarch,
|
||||
+ gdbarch_read_core_file_mappings_ftype read_core_file_mappings)
|
||||
+{
|
||||
+ gdbarch->read_core_file_mappings = read_core_file_mappings;
|
||||
+}
|
||||
+
|
||||
|
||||
/* Keep a registry of per-architecture data-pointers required by GDB
|
||||
modules. */
|
||||
diff --git a/gdb/gdbarch.h b/gdb/gdbarch.h
|
||||
--- a/gdb/gdbarch.h
|
||||
+++ b/gdb/gdbarch.h
|
||||
@@ -1640,6 +1640,12 @@ typedef std::string (gdbarch_get_pc_address_flags_ftype) (frame_info *frame, COR
|
||||
extern std::string gdbarch_get_pc_address_flags (struct gdbarch *gdbarch, frame_info *frame, CORE_ADDR pc);
|
||||
extern void set_gdbarch_get_pc_address_flags (struct gdbarch *gdbarch, gdbarch_get_pc_address_flags_ftype *get_pc_address_flags);
|
||||
|
||||
+/* Read core file mappings */
|
||||
+
|
||||
+typedef void (gdbarch_read_core_file_mappings_ftype) (struct gdbarch *gdbarch, struct bfd *cbfd,gdb::function_view<void (ULONGEST count)> pre_loop_cb,gdb::function_view<void (int num, ULONGEST start, ULONGEST end, ULONGEST file_ofs, const char *filename, const void *other)> loop_cb);
|
||||
+extern void gdbarch_read_core_file_mappings (struct gdbarch *gdbarch, struct bfd *cbfd,gdb::function_view<void (ULONGEST count)> pre_loop_cb,gdb::function_view<void (int num, ULONGEST start, ULONGEST end, ULONGEST file_ofs, const char *filename, const void *other)> loop_cb);
|
||||
+extern void set_gdbarch_read_core_file_mappings (struct gdbarch *gdbarch, gdbarch_read_core_file_mappings_ftype *read_core_file_mappings);
|
||||
+
|
||||
extern struct gdbarch_tdep *gdbarch_tdep (struct gdbarch *gdbarch);
|
||||
|
||||
|
||||
diff --git a/gdb/gdbarch.sh b/gdb/gdbarch.sh
|
||||
--- a/gdb/gdbarch.sh
|
||||
+++ b/gdb/gdbarch.sh
|
||||
@@ -1209,6 +1209,9 @@ m;ULONGEST;type_align;struct type *type;type;;default_type_align;;0
|
||||
# Return a string containing any flags for the given PC in the given FRAME.
|
||||
f;std::string;get_pc_address_flags;frame_info *frame, CORE_ADDR pc;frame, pc;;default_get_pc_address_flags;;0
|
||||
|
||||
+# Read core file mappings
|
||||
+m;void;read_core_file_mappings;struct bfd *cbfd,gdb::function_view<void (ULONGEST count)> pre_loop_cb,gdb::function_view<void (int num, ULONGEST start, ULONGEST end, ULONGEST file_ofs, const char *filename, const void *other)> loop_cb;cbfd, pre_loop_cb, loop_cb;;default_read_core_file_mappings;;0
|
||||
+
|
||||
EOF
|
||||
}
|
||||
|
531
SOURCES/gdb-rhbz1842691-corefile-mem-access-8of15.patch
Normal file
531
SOURCES/gdb-rhbz1842691-corefile-mem-access-8of15.patch
Normal file
@ -0,0 +1,531 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 27 Jul 2020 18:51:07 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-8of15.patch
|
||||
|
||||
;; Use NT_FILE note section for reading core target memory
|
||||
;; Kevin Buettner, RH BZ 1842961
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Thu Jun 11 19:20:03 2020 -0700
|
||||
|
||||
Use NT_FILE note section for reading core target memory
|
||||
|
||||
In his reviews of my v1 and v2 corefile related patches, Pedro
|
||||
identified two cases which weren't handled by those patches.
|
||||
|
||||
In https://sourceware.org/pipermail/gdb-patches/2020-May/168826.html,
|
||||
Pedro showed that debugging a core file in which mmap() is used to
|
||||
create a new mapping over an existing file-backed mapping will
|
||||
produce incorrect results. I.e, for his example, GDB would
|
||||
show:
|
||||
|
||||
(gdb) disassemble main
|
||||
Dump of assembler code for function main:
|
||||
0x00000000004004e6 <+0>: push %rbp
|
||||
0x00000000004004e7 <+1>: mov %rsp,%rbp
|
||||
=> 0x00000000004004ea <+4>: callq 0x4003f0 <abort@plt>
|
||||
End of assembler dump.
|
||||
|
||||
This sort of looks like it might be correct, but is not due to the
|
||||
fact that mmap(...MAP_FIXED...) was used to create a mapping (of all
|
||||
zeros) on top of the .text section. So, the correct result should be:
|
||||
|
||||
(gdb) disassemble main
|
||||
Dump of assembler code for function main:
|
||||
0x00000000004004e6 <+0>: add %al,(%rax)
|
||||
0x00000000004004e8 <+2>: add %al,(%rax)
|
||||
=> 0x00000000004004ea <+4>: add %al,(%rax)
|
||||
0x00000000004004ec <+6>: add %al,(%rax)
|
||||
0x00000000004004ee <+8>: add %al,(%rax)
|
||||
End of assembler dump.
|
||||
|
||||
The other case that Pedro found involved an attempted examination of a
|
||||
particular section in the test case from gdb.base/corefile.exp. On
|
||||
Fedora 27 or 28, the following behavior may be observed:
|
||||
|
||||
(gdb) info proc mappings
|
||||
Mapped address spaces:
|
||||
|
||||
Start Addr End Addr Size Offset objfile
|
||||
...
|
||||
0x7ffff7839000 0x7ffff7a38000 0x1ff000 0x1b5000 /usr/lib64/libc-2.27.so
|
||||
...
|
||||
(gdb) x/4x 0x7ffff7839000
|
||||
0x7ffff7839000: Cannot access memory at address 0x7ffff7839000
|
||||
|
||||
FYI, this section appears to be unrelocated vtable data. See
|
||||
https://sourceware.org/pipermail/gdb-patches/2020-May/168331.html for
|
||||
a detailed analysis.
|
||||
|
||||
The important thing here is that GDB should be able to access this
|
||||
address since it should be backed by the shared library. I.e. it
|
||||
should do this:
|
||||
|
||||
(gdb) x/4x 0x7ffff7839000
|
||||
0x7ffff7839000: 0x0007ddf0 0x00000000 0x0007dba0 0x00000000
|
||||
|
||||
Both of these cases are fixed with this commit.
|
||||
|
||||
In a nutshell, this commit opens a "binary" target BFD for each of the
|
||||
files that are mentioned in an NT_FILE / .note.linuxcore.file note
|
||||
section. It then uses these mappings instead of the file stratum
|
||||
mappings that GDB has used in the past.
|
||||
|
||||
If this note section doesn't exist or is mangled for some reason, then
|
||||
GDB will use the file stratum as before. Should this happen, then
|
||||
we can expect both of the above problems to again be present.
|
||||
|
||||
See the code comments in the commit for other details.
|
||||
|
||||
gdb/ChangeLog:
|
||||
|
||||
* corelow.c (solist.h, unordered_map): Include.
|
||||
(class core_target): Add field m_core_file_mappings and
|
||||
method build_file_mappings.
|
||||
(core_target::core_target): Call build_file_mappings.
|
||||
(core_target::~core_target): Free memory associated with
|
||||
m_core_file_mappings.
|
||||
(core_target::build_file_mappings): New method.
|
||||
(core_target::xfer_partial): Use m_core_file_mappings
|
||||
for memory transfers.
|
||||
* linux-tdep.c (linux_read_core_file_mappings): New
|
||||
function.
|
||||
(linux_core_info_proc_mappings): Rewrite to use
|
||||
linux_read_core_file_mappings.
|
||||
(linux_init_abi): Register linux_read_core_file_mappings.
|
||||
|
||||
diff --git a/gdb/corelow.c b/gdb/corelow.c
|
||||
--- a/gdb/corelow.c
|
||||
+++ b/gdb/corelow.c
|
||||
@@ -41,6 +41,7 @@
|
||||
#include "exec.h"
|
||||
#include "readline/tilde.h"
|
||||
#include "solib.h"
|
||||
+#include "solist.h"
|
||||
#include "filenames.h"
|
||||
#include "progspace.h"
|
||||
#include "objfiles.h"
|
||||
@@ -48,6 +49,8 @@
|
||||
#include "completer.h"
|
||||
#include "gdbsupport/filestuff.h"
|
||||
#include "build-id.h"
|
||||
+#include "gdbsupport/pathstuff.h"
|
||||
+#include <unordered_map>
|
||||
|
||||
#ifndef O_LARGEFILE
|
||||
#define O_LARGEFILE 0
|
||||
@@ -132,6 +135,13 @@ private: /* per-core data */
|
||||
core file currently open on core_bfd. */
|
||||
core_fns *m_core_vec = NULL;
|
||||
|
||||
+ /* File-backed address space mappings: some core files include
|
||||
+ information about memory mapped files. */
|
||||
+ target_section_table m_core_file_mappings {};
|
||||
+
|
||||
+ /* Build m_core_file_mappings. Called from the constructor. */
|
||||
+ void build_file_mappings ();
|
||||
+
|
||||
/* FIXME: kettenis/20031023: Eventually this field should
|
||||
disappear. */
|
||||
struct gdbarch *m_core_gdbarch = NULL;
|
||||
@@ -150,11 +160,120 @@ core_target::core_target ()
|
||||
&m_core_section_table.sections_end))
|
||||
error (_("\"%s\": Can't find sections: %s"),
|
||||
bfd_get_filename (core_bfd), bfd_errmsg (bfd_get_error ()));
|
||||
+
|
||||
+ build_file_mappings ();
|
||||
}
|
||||
|
||||
core_target::~core_target ()
|
||||
{
|
||||
xfree (m_core_section_table.sections);
|
||||
+ xfree (m_core_file_mappings.sections);
|
||||
+}
|
||||
+
|
||||
+/* Construct the target_section_table for file-backed mappings if
|
||||
+ they exist.
|
||||
+
|
||||
+ For each unique path in the note, we'll open a BFD with a bfd
|
||||
+ target of "binary". This is an unstructured bfd target upon which
|
||||
+ we'll impose a structure from the mappings in the architecture-specific
|
||||
+ mappings note. A BFD section is allocated and initialized for each
|
||||
+ file-backed mapping.
|
||||
+
|
||||
+ We take care to not share already open bfds with other parts of
|
||||
+ GDB; in particular, we don't want to add new sections to existing
|
||||
+ BFDs. We do, however, ensure that the BFDs that we allocate here
|
||||
+ will go away (be deallocated) when the core target is detached. */
|
||||
+
|
||||
+void
|
||||
+core_target::build_file_mappings ()
|
||||
+{
|
||||
+ std::unordered_map<std::string, struct bfd *> bfd_map;
|
||||
+
|
||||
+ /* See linux_read_core_file_mappings() in linux-tdep.c for an example
|
||||
+ read_core_file_mappings method. */
|
||||
+ gdbarch_read_core_file_mappings (m_core_gdbarch, core_bfd,
|
||||
+
|
||||
+ /* After determining the number of mappings, read_core_file_mappings
|
||||
+ will invoke this lambda which allocates target_section storage for
|
||||
+ the mappings. */
|
||||
+ [&] (ULONGEST count)
|
||||
+ {
|
||||
+ m_core_file_mappings.sections = XNEWVEC (struct target_section, count);
|
||||
+ m_core_file_mappings.sections_end = m_core_file_mappings.sections;
|
||||
+ },
|
||||
+
|
||||
+ /* read_core_file_mappings will invoke this lambda for each mapping
|
||||
+ that it finds. */
|
||||
+ [&] (int num, ULONGEST start, ULONGEST end, ULONGEST file_ofs,
|
||||
+ const char *filename, const void *other)
|
||||
+ {
|
||||
+ /* Architecture-specific read_core_mapping methods are expected to
|
||||
+ weed out non-file-backed mappings. */
|
||||
+ gdb_assert (filename != nullptr);
|
||||
+
|
||||
+ struct bfd *bfd = bfd_map[filename];
|
||||
+ if (bfd == nullptr)
|
||||
+ {
|
||||
+ /* Use exec_file_find() to do sysroot expansion. It'll
|
||||
+ also strip the potential sysroot "target:" prefix. If
|
||||
+ there is no sysroot, an equivalent (possibly more
|
||||
+ canonical) pathname will be provided. */
|
||||
+ gdb::unique_xmalloc_ptr<char> expanded_fname
|
||||
+ = exec_file_find (filename, NULL);
|
||||
+ if (expanded_fname == nullptr)
|
||||
+ {
|
||||
+ warning (_("Can't open file %s during file-backed mapping "
|
||||
+ "note processing"),
|
||||
+ expanded_fname.get ());
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
+ bfd = bfd_map[filename] = bfd_openr (expanded_fname.get (),
|
||||
+ "binary");
|
||||
+
|
||||
+ if (bfd == nullptr || !bfd_check_format (bfd, bfd_object))
|
||||
+ {
|
||||
+ /* If we get here, there's a good chance that it's due to
|
||||
+ an internal error. We issue a warning instead of an
|
||||
+ internal error because of the possibility that the
|
||||
+ file was removed in between checking for its
|
||||
+ existence during the expansion in exec_file_find()
|
||||
+ and the calls to bfd_openr() / bfd_check_format().
|
||||
+ Output both the path from the core file note along
|
||||
+ with its expansion to make debugging this problem
|
||||
+ easier. */
|
||||
+ warning (_("Can't open file %s which was expanded to %s "
|
||||
+ "during file-backed mapping note processing"),
|
||||
+ filename, expanded_fname.get ());
|
||||
+ if (bfd != nullptr)
|
||||
+ bfd_close (bfd);
|
||||
+ return;
|
||||
+ }
|
||||
+ /* Ensure that the bfd will be closed when core_bfd is closed.
|
||||
+ This can be checked before/after a core file detach via
|
||||
+ "maint info bfds". */
|
||||
+ gdb_bfd_record_inclusion (core_bfd, bfd);
|
||||
+ }
|
||||
+
|
||||
+ /* Make new BFD section. All sections have the same name,
|
||||
+ which is permitted by bfd_make_section_anyway(). */
|
||||
+ asection *sec = bfd_make_section_anyway (bfd, "load");
|
||||
+ if (sec == nullptr)
|
||||
+ error (_("Can't make section"));
|
||||
+ sec->filepos = file_ofs;
|
||||
+ bfd_set_section_flags (sec, SEC_READONLY | SEC_HAS_CONTENTS);
|
||||
+ bfd_set_section_size (sec, end - start);
|
||||
+ bfd_set_section_vma (sec, start);
|
||||
+ bfd_set_section_lma (sec, start);
|
||||
+ bfd_set_section_alignment (sec, 2);
|
||||
+
|
||||
+ /* Set target_section fields. */
|
||||
+ struct target_section *ts = m_core_file_mappings.sections_end++;
|
||||
+ ts->addr = start;
|
||||
+ ts->endaddr = end;
|
||||
+ ts->owner = nullptr;
|
||||
+ ts->the_bfd_section = sec;
|
||||
+ });
|
||||
}
|
||||
|
||||
/* List of all available core_fns. On gdb startup, each core file
|
||||
@@ -773,10 +892,21 @@ core_target::xfer_partial (enum target_object object, const char *annex,
|
||||
if (xfer_status == TARGET_XFER_OK)
|
||||
return TARGET_XFER_OK;
|
||||
|
||||
- /* Now check the stratum beneath us; this should be file_stratum. */
|
||||
- xfer_status = this->beneath ()->xfer_partial (object, annex, readbuf,
|
||||
- writebuf, offset, len,
|
||||
- xfered_len);
|
||||
+ /* Check file backed mappings. If they're available, use
|
||||
+ core file provided mappings (e.g. from .note.linuxcore.file
|
||||
+ or the like) as this should provide a more accurate
|
||||
+ result. If not, check the stratum beneath us, which should
|
||||
+ be the file stratum. */
|
||||
+ if (m_core_file_mappings.sections != nullptr)
|
||||
+ xfer_status = section_table_xfer_memory_partial
|
||||
+ (readbuf, writebuf,
|
||||
+ offset, len, xfered_len,
|
||||
+ m_core_file_mappings.sections,
|
||||
+ m_core_file_mappings.sections_end);
|
||||
+ else
|
||||
+ xfer_status = this->beneath ()->xfer_partial (object, annex, readbuf,
|
||||
+ writebuf, offset, len,
|
||||
+ xfered_len);
|
||||
if (xfer_status == TARGET_XFER_OK)
|
||||
return TARGET_XFER_OK;
|
||||
|
||||
diff --git a/gdb/linux-tdep.c b/gdb/linux-tdep.c
|
||||
--- a/gdb/linux-tdep.c
|
||||
+++ b/gdb/linux-tdep.c
|
||||
@@ -1024,106 +1024,174 @@ linux_info_proc (struct gdbarch *gdbarch, const char *args,
|
||||
}
|
||||
}
|
||||
|
||||
-/* Implement "info proc mappings" for a corefile. */
|
||||
+/* Implementation of `gdbarch_read_core_file_mappings', as defined in
|
||||
+ gdbarch.h.
|
||||
+
|
||||
+ This function reads the NT_FILE note (which BFD turns into the
|
||||
+ section ".note.linuxcore.file"). The format of this note / section
|
||||
+ is described as follows in the Linux kernel sources in
|
||||
+ fs/binfmt_elf.c:
|
||||
+
|
||||
+ long count -- how many files are mapped
|
||||
+ long page_size -- units for file_ofs
|
||||
+ array of [COUNT] elements of
|
||||
+ long start
|
||||
+ long end
|
||||
+ long file_ofs
|
||||
+ followed by COUNT filenames in ASCII: "FILE1" NUL "FILE2" NUL...
|
||||
+
|
||||
+ CBFD is the BFD of the core file.
|
||||
+
|
||||
+ PRE_LOOP_CB is the callback function to invoke prior to starting
|
||||
+ the loop which processes individual entries. This callback will
|
||||
+ only be executed after the note has been examined in enough
|
||||
+ detail to verify that it's not malformed in some way.
|
||||
+
|
||||
+ LOOP_CB is the callback function that will be executed once
|
||||
+ for each mapping. */
|
||||
|
||||
static void
|
||||
-linux_core_info_proc_mappings (struct gdbarch *gdbarch, const char *args)
|
||||
+linux_read_core_file_mappings (struct gdbarch *gdbarch,
|
||||
+ struct bfd *cbfd,
|
||||
+ gdb::function_view<void (ULONGEST count)>
|
||||
+ pre_loop_cb,
|
||||
+ gdb::function_view<void (int num,
|
||||
+ ULONGEST start,
|
||||
+ ULONGEST end,
|
||||
+ ULONGEST file_ofs,
|
||||
+ const char *filename,
|
||||
+ const void *other)>
|
||||
+ loop_cb)
|
||||
{
|
||||
- asection *section;
|
||||
- ULONGEST count, page_size;
|
||||
- unsigned char *descdata, *filenames, *descend;
|
||||
- size_t note_size;
|
||||
- unsigned int addr_size_bits, addr_size;
|
||||
- struct gdbarch *core_gdbarch = gdbarch_from_bfd (core_bfd);
|
||||
- /* We assume this for reading 64-bit core files. */
|
||||
+ /* Ensure that ULONGEST is big enough for reading 64-bit core files. */
|
||||
gdb_static_assert (sizeof (ULONGEST) >= 8);
|
||||
|
||||
- section = bfd_get_section_by_name (core_bfd, ".note.linuxcore.file");
|
||||
- if (section == NULL)
|
||||
- {
|
||||
- warning (_("unable to find mappings in core file"));
|
||||
- return;
|
||||
- }
|
||||
+ /* It's not required that the NT_FILE note exists, so return silently
|
||||
+ if it's not found. Beyond this point though, we'll complain
|
||||
+ if problems are found. */
|
||||
+ asection *section = bfd_get_section_by_name (cbfd, ".note.linuxcore.file");
|
||||
+ if (section == nullptr)
|
||||
+ return;
|
||||
|
||||
- addr_size_bits = gdbarch_addr_bit (core_gdbarch);
|
||||
- addr_size = addr_size_bits / 8;
|
||||
- note_size = bfd_section_size (section);
|
||||
+ unsigned int addr_size_bits = gdbarch_addr_bit (gdbarch);
|
||||
+ unsigned int addr_size = addr_size_bits / 8;
|
||||
+ size_t note_size = bfd_section_size (section);
|
||||
|
||||
if (note_size < 2 * addr_size)
|
||||
- error (_("malformed core note - too short for header"));
|
||||
+ {
|
||||
+ warning (_("malformed core note - too short for header"));
|
||||
+ return;
|
||||
+ }
|
||||
|
||||
- gdb::def_vector<unsigned char> contents (note_size);
|
||||
+ gdb::def_vector<gdb_byte> contents (note_size);
|
||||
if (!bfd_get_section_contents (core_bfd, section, contents.data (),
|
||||
0, note_size))
|
||||
- error (_("could not get core note contents"));
|
||||
+ {
|
||||
+ warning (_("could not get core note contents"));
|
||||
+ return;
|
||||
+ }
|
||||
|
||||
- descdata = contents.data ();
|
||||
- descend = descdata + note_size;
|
||||
+ gdb_byte *descdata = contents.data ();
|
||||
+ char *descend = (char *) descdata + note_size;
|
||||
|
||||
if (descdata[note_size - 1] != '\0')
|
||||
- error (_("malformed note - does not end with \\0"));
|
||||
+ {
|
||||
+ warning (_("malformed note - does not end with \\0"));
|
||||
+ return;
|
||||
+ }
|
||||
|
||||
- count = bfd_get (addr_size_bits, core_bfd, descdata);
|
||||
+ ULONGEST count = bfd_get (addr_size_bits, core_bfd, descdata);
|
||||
descdata += addr_size;
|
||||
|
||||
- page_size = bfd_get (addr_size_bits, core_bfd, descdata);
|
||||
+ ULONGEST page_size = bfd_get (addr_size_bits, core_bfd, descdata);
|
||||
descdata += addr_size;
|
||||
|
||||
if (note_size < 2 * addr_size + count * 3 * addr_size)
|
||||
- error (_("malformed note - too short for supplied file count"));
|
||||
-
|
||||
- printf_filtered (_("Mapped address spaces:\n\n"));
|
||||
- if (gdbarch_addr_bit (gdbarch) == 32)
|
||||
- {
|
||||
- printf_filtered ("\t%10s %10s %10s %10s %s\n",
|
||||
- "Start Addr",
|
||||
- " End Addr",
|
||||
- " Size", " Offset", "objfile");
|
||||
- }
|
||||
- else
|
||||
{
|
||||
- printf_filtered (" %18s %18s %10s %10s %s\n",
|
||||
- "Start Addr",
|
||||
- " End Addr",
|
||||
- " Size", " Offset", "objfile");
|
||||
+ warning (_("malformed note - too short for supplied file count"));
|
||||
+ return;
|
||||
}
|
||||
|
||||
- filenames = descdata + count * 3 * addr_size;
|
||||
- while (--count > 0)
|
||||
+ char *filenames = (char *) descdata + count * 3 * addr_size;
|
||||
+
|
||||
+ /* Make sure that the correct number of filenames exist. Complain
|
||||
+ if there aren't enough or are too many. */
|
||||
+ char *f = filenames;
|
||||
+ for (int i = 0; i < count; i++)
|
||||
{
|
||||
- ULONGEST start, end, file_ofs;
|
||||
+ if (f >= descend)
|
||||
+ {
|
||||
+ warning (_("malformed note - filename area is too small"));
|
||||
+ return;
|
||||
+ }
|
||||
+ f += strnlen (f, descend - f) + 1;
|
||||
+ }
|
||||
+ /* Complain, but don't return early if the filename area is too big. */
|
||||
+ if (f != descend)
|
||||
+ warning (_("malformed note - filename area is too big"));
|
||||
|
||||
- if (filenames == descend)
|
||||
- error (_("malformed note - filenames end too early"));
|
||||
+ pre_loop_cb (count);
|
||||
|
||||
- start = bfd_get (addr_size_bits, core_bfd, descdata);
|
||||
+ for (int i = 0; i < count; i++)
|
||||
+ {
|
||||
+ ULONGEST start = bfd_get (addr_size_bits, core_bfd, descdata);
|
||||
descdata += addr_size;
|
||||
- end = bfd_get (addr_size_bits, core_bfd, descdata);
|
||||
+ ULONGEST end = bfd_get (addr_size_bits, core_bfd, descdata);
|
||||
descdata += addr_size;
|
||||
- file_ofs = bfd_get (addr_size_bits, core_bfd, descdata);
|
||||
+ ULONGEST file_ofs
|
||||
+ = bfd_get (addr_size_bits, core_bfd, descdata) * page_size;
|
||||
descdata += addr_size;
|
||||
+ char * filename = filenames;
|
||||
+ filenames += strlen ((char *) filenames) + 1;
|
||||
|
||||
- file_ofs *= page_size;
|
||||
-
|
||||
- if (gdbarch_addr_bit (gdbarch) == 32)
|
||||
- printf_filtered ("\t%10s %10s %10s %10s %s\n",
|
||||
- paddress (gdbarch, start),
|
||||
- paddress (gdbarch, end),
|
||||
- hex_string (end - start),
|
||||
- hex_string (file_ofs),
|
||||
- filenames);
|
||||
- else
|
||||
- printf_filtered (" %18s %18s %10s %10s %s\n",
|
||||
- paddress (gdbarch, start),
|
||||
- paddress (gdbarch, end),
|
||||
- hex_string (end - start),
|
||||
- hex_string (file_ofs),
|
||||
- filenames);
|
||||
-
|
||||
- filenames += 1 + strlen ((char *) filenames);
|
||||
+ loop_cb (i, start, end, file_ofs, filename, nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
+/* Implement "info proc mappings" for a corefile. */
|
||||
+
|
||||
+static void
|
||||
+linux_core_info_proc_mappings (struct gdbarch *gdbarch, const char *args)
|
||||
+{
|
||||
+ linux_read_core_file_mappings (gdbarch, core_bfd,
|
||||
+ [=] (ULONGEST count)
|
||||
+ {
|
||||
+ printf_filtered (_("Mapped address spaces:\n\n"));
|
||||
+ if (gdbarch_addr_bit (gdbarch) == 32)
|
||||
+ {
|
||||
+ printf_filtered ("\t%10s %10s %10s %10s %s\n",
|
||||
+ "Start Addr",
|
||||
+ " End Addr",
|
||||
+ " Size", " Offset", "objfile");
|
||||
+ }
|
||||
+ else
|
||||
+ {
|
||||
+ printf_filtered (" %18s %18s %10s %10s %s\n",
|
||||
+ "Start Addr",
|
||||
+ " End Addr",
|
||||
+ " Size", " Offset", "objfile");
|
||||
+ }
|
||||
+ },
|
||||
+ [=] (int num, ULONGEST start, ULONGEST end, ULONGEST file_ofs,
|
||||
+ const char *filename, const void *other)
|
||||
+ {
|
||||
+ if (gdbarch_addr_bit (gdbarch) == 32)
|
||||
+ printf_filtered ("\t%10s %10s %10s %10s %s\n",
|
||||
+ paddress (gdbarch, start),
|
||||
+ paddress (gdbarch, end),
|
||||
+ hex_string (end - start),
|
||||
+ hex_string (file_ofs),
|
||||
+ filename);
|
||||
+ else
|
||||
+ printf_filtered (" %18s %18s %10s %10s %s\n",
|
||||
+ paddress (gdbarch, start),
|
||||
+ paddress (gdbarch, end),
|
||||
+ hex_string (end - start),
|
||||
+ hex_string (file_ofs),
|
||||
+ filename);
|
||||
+ });
|
||||
+}
|
||||
+
|
||||
/* Implement "info proc" for a corefile. */
|
||||
|
||||
static void
|
||||
@@ -2471,6 +2539,7 @@ linux_init_abi (struct gdbarch_info info, struct gdbarch *gdbarch)
|
||||
set_gdbarch_info_proc (gdbarch, linux_info_proc);
|
||||
set_gdbarch_core_info_proc (gdbarch, linux_core_info_proc);
|
||||
set_gdbarch_core_xfer_siginfo (gdbarch, linux_core_xfer_siginfo);
|
||||
+ set_gdbarch_read_core_file_mappings (gdbarch, linux_read_core_file_mappings);
|
||||
set_gdbarch_find_memory_regions (gdbarch, linux_find_memory_regions);
|
||||
set_gdbarch_make_corefile_notes (gdbarch, linux_make_corefile_notes);
|
||||
set_gdbarch_has_shared_address_space (gdbarch,
|
101
SOURCES/gdb-rhbz1842691-corefile-mem-access-9of15.patch
Normal file
101
SOURCES/gdb-rhbz1842691-corefile-mem-access-9of15.patch
Normal file
@ -0,0 +1,101 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 27 Jul 2020 19:21:54 -0400
|
||||
Subject: gdb-rhbz1842691-corefile-mem-access-9of15.patch
|
||||
|
||||
;; Add test for accessing read-only mmapped data in a core file
|
||||
;; Kevin Buettner, RH BZ 1842691
|
||||
|
||||
Author: Kevin Buettner <kevinb@redhat.com>
|
||||
Date: Tue Jun 16 11:39:22 2020 -0700
|
||||
|
||||
Add test for accessing read-only mmapped data in a core file
|
||||
|
||||
This test passes when run using a GDB with my corefile patches. When
|
||||
run against a GDB without my patches, I see the following failures,
|
||||
the first of which is due to the test added by this commit:
|
||||
|
||||
FAIL: gdb.base/corefile.exp: accessing read-only mmapped data in core file (
|
||||
FAIL: gdb.base/corefile.exp: accessing anonymous, unwritten-to mmap data
|
||||
|
||||
gdb/testsuite/ChangeLog:
|
||||
|
||||
* gdb.base/corefile.exp: Add test "accessing read-only mmapped
|
||||
data in core file".
|
||||
* gdb.base/coremaker.c (buf2ro): New global.
|
||||
(mmapdata): Add a read-only mmap mapping.
|
||||
|
||||
diff --git a/gdb/testsuite/gdb.base/corefile.exp b/gdb/testsuite/gdb.base/corefile.exp
|
||||
--- a/gdb/testsuite/gdb.base/corefile.exp
|
||||
+++ b/gdb/testsuite/gdb.base/corefile.exp
|
||||
@@ -34,7 +34,10 @@ if {[build_executable $testfile.exp $testfile $srcfile debug] == -1} {
|
||||
return -1
|
||||
}
|
||||
|
||||
-set corefile [core_find $binfile {coremmap.data}]
|
||||
+# Do not delete coremap.data when calling core_find. This file is
|
||||
+# required for GDB to find mmap'd data in the "accessing read-only
|
||||
+# mmapped data in core file" test.
|
||||
+set corefile [core_find $binfile {}]
|
||||
if {$corefile == ""} {
|
||||
return 0
|
||||
}
|
||||
@@ -175,6 +178,19 @@ gdb_test_multiple "x/8bd buf2" "$test" {
|
||||
}
|
||||
}
|
||||
|
||||
+set test "accessing read-only mmapped data in core file"
|
||||
+gdb_test_multiple "x/8bd buf2ro" "$test" {
|
||||
+ -re ".*:.*0.*1.*2.*3.*4.*5.*6.*7.*$gdb_prompt $" {
|
||||
+ pass "$test"
|
||||
+ }
|
||||
+ -re "0x\[f\]*:.*Cannot access memory at address 0x\[f\]*.*$gdb_prompt $" {
|
||||
+ fail "$test (mapping failed at runtime)"
|
||||
+ }
|
||||
+ -re "0x.*:.*Cannot access memory at address 0x.*$gdb_prompt $" {
|
||||
+ fail "$test (mapping address not found in core file)"
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
# Test ability to read anonymous and, more importantly, unwritten-to
|
||||
# mmap'd data.
|
||||
|
||||
diff --git a/gdb/testsuite/gdb.base/coremaker.c b/gdb/testsuite/gdb.base/coremaker.c
|
||||
--- a/gdb/testsuite/gdb.base/coremaker.c
|
||||
+++ b/gdb/testsuite/gdb.base/coremaker.c
|
||||
@@ -38,6 +38,7 @@
|
||||
|
||||
char *buf1;
|
||||
char *buf2;
|
||||
+char *buf2ro;
|
||||
char *buf3;
|
||||
|
||||
int coremaker_data = 1; /* In Data section */
|
||||
@@ -90,16 +91,25 @@ mmapdata ()
|
||||
return;
|
||||
}
|
||||
|
||||
+ /* Map in another copy, read-only. We won't write to this copy so it
|
||||
+ will likely not end up in the core file. */
|
||||
+ buf2ro = (char *) mmap (0, MAPSIZE, PROT_READ, MAP_PRIVATE, fd, 0);
|
||||
+ if (buf2ro == (char *) -1)
|
||||
+ {
|
||||
+ perror ("mmap failed");
|
||||
+ return;
|
||||
+ }
|
||||
+
|
||||
/* Verify that the original data and the mapped data are identical.
|
||||
If not, we'd rather fail now than when trying to access the mapped
|
||||
data from the core file. */
|
||||
|
||||
for (j = 0; j < MAPSIZE; ++j)
|
||||
{
|
||||
- if (buf1[j] != buf2[j])
|
||||
+ if (buf1[j] != buf2[j] || buf1[j] != buf2ro[j])
|
||||
{
|
||||
fprintf (stderr, "mapped data is incorrect");
|
||||
- buf2 = (char *) -1;
|
||||
+ buf2 = buf2ro = (char *) -1;
|
||||
return;
|
||||
}
|
||||
}
|
@ -6,10 +6,9 @@ Subject: gdb-rhbz1844458-use-fputX_unfiltered.patch
|
||||
;; Fix fput?_unfiltered functions
|
||||
;; RH BZ 1844458 (Sergio Durigan Junior and Tom Tromey)
|
||||
|
||||
From 9effb44ccbf50c16da66aaab5fd535fe17e38e32 Mon Sep 17 00:00:00 2001
|
||||
From: Sergio Durigan Junior <sergiodj@redhat.com>
|
||||
Date: Wed, 19 Feb 2020 16:40:48 -0500
|
||||
Subject: [PATCH] Make '{putchar,fputc}_unfiltered' use 'fputs_unfiltered'
|
||||
From: Sergio Durigan Junior <sergiodj@redhat.com>
|
||||
Date: Wed, 19 Feb 2020 16:40:48 -0500
|
||||
Subject: [PATCH] Make '{putchar,fputc}_unfiltered' use 'fputs_unfiltered'
|
||||
|
||||
There is currently a regression when using
|
||||
'{putchar,fputc}_unfiltered' with 'puts_unfiltered' which was
|
||||
|
@ -0,0 +1,67 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Mon, 16 Nov 2020 12:42:09 -0500
|
||||
Subject: gdb-rhbz1898252-loadable-section-outside-ELF-segments.patch
|
||||
|
||||
;; Backport of "Exclude debuginfo files from 'outside of ELF segments'
|
||||
;; warning" (Keith Seitz)
|
||||
|
||||
Exclude debuginfo files from "outside of ELF segments" warning
|
||||
|
||||
When GDB loads an ELF file, it will warn when a section is not located
|
||||
in an ELF segment:
|
||||
|
||||
$ ./gdb -q -iex "set build-id-verbose 0" --ex "b systemctl_main" -ex "r" -batch --args systemctl kexec
|
||||
Breakpoint 1 at 0xc24d: file ../src/systemctl/systemctl.c, line 8752.
|
||||
warning: Loadable section ".note.gnu.property" outside of ELF segments
|
||||
in .gnu_debugdata for /lib64/libgcc_s.so.1
|
||||
[Thread debugging using libthread_db enabled]
|
||||
Using host libthread_db library "/lib64/libthread_db.so.1".
|
||||
warning: Loadable section ".note.gnu.property" outside of ELF segments
|
||||
in .gnu_debugdata for /lib64/libcap.so.2
|
||||
warning: Loadable section ".note.gnu.property" outside of ELF segments
|
||||
in .gnu_debugdata for /lib64/libacl.so.1
|
||||
warning: Loadable section ".note.gnu.property" outside of ELF segments
|
||||
in .gnu_debugdata for /lib64/libcryptsetup.so.12
|
||||
warning: Loadable section ".note.gnu.property" outside of ELF segments
|
||||
in .gnu_debugdata for /lib64/libgcrypt.so.20
|
||||
warning: Loadable section ".note.gnu.property" outside of ELF segments
|
||||
in .gnu_debugdata for /lib64/libip4tc.so.2
|
||||
[snip]
|
||||
This has feature has also been reported by various users, most notably
|
||||
the Fedora-EOL'd bug 1553086.
|
||||
|
||||
Mark Wielaard explains the issue quite nicely in
|
||||
|
||||
https://sourceware.org/bugzilla/show_bug.cgi?id=24717#c2
|
||||
|
||||
The short of it is, the ELF program headers for debuginfo files are
|
||||
not suited to this particular use case. Consequently, the warning
|
||||
generated above really is useless and should be ignored.
|
||||
|
||||
This patch follows the same heuristic that BFD itself uses.
|
||||
|
||||
gdb/ChangeLog
|
||||
2020-11-13 Keith Seitz <keiths@redhat.com>
|
||||
|
||||
https://bugzilla.redhat.com/show_bug.cgi?id=1553086
|
||||
* elfread.c (elf_symfile_segments): Omit "Loadable section ...
|
||||
outside of ELF segments" warning for debugin
|
||||
|
||||
diff --git a/gdb/elfread.c b/gdb/elfread.c
|
||||
--- a/gdb/elfread.c
|
||||
+++ b/gdb/elfread.c
|
||||
@@ -151,7 +151,12 @@ elf_symfile_segments (bfd *abfd)
|
||||
RealView) use SHT_NOBITS for uninitialized data. Since it is
|
||||
uninitialized, it doesn't need a program header. Such
|
||||
binaries are not relocatable. */
|
||||
- if (bfd_section_size (sect) > 0 && j == num_segments
|
||||
+
|
||||
+ /* Exclude debuginfo files from this warning, too, since those
|
||||
+ are often not strictly compliant with the standard. See, e.g.,
|
||||
+ ld/24717 for more discussion. */
|
||||
+ if (!is_debuginfo_file (abfd)
|
||||
+ && bfd_section_size (sect) > 0 && j == num_segments
|
||||
&& (bfd_section_flags (sect) & SEC_LOAD) != 0)
|
||||
warning (_("Loadable section \"%s\" outside of ELF segments"),
|
||||
bfd_section_name (sect));
|
64
SOURCES/gdb-rhbz1903375-s390x-store-on-condition.patch
Normal file
64
SOURCES/gdb-rhbz1903375-s390x-store-on-condition.patch
Normal file
@ -0,0 +1,64 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Andreas Arnez <arnez@linux.ibm.com>
|
||||
Date: Thu, 19 Nov 2020 19:10:58 +0100
|
||||
Subject: gdb-rhbz1903375-s390x-store-on-condition.patch
|
||||
|
||||
;; Backport of "Correct recording of 'store on condition' insns"
|
||||
;; Andreas Arnaz (RH BZ 1903374)
|
||||
|
||||
gdb/s390: Correct recording of "store on condition" insns
|
||||
|
||||
The "store on condition" instructions STOC, STOCG, and STOCFH are recorded
|
||||
as if their instruction formats resembled that of STG. This is wrong,
|
||||
usually resulting in "failed to record execution log" errors when trying
|
||||
to record code with any of these instructions.
|
||||
|
||||
This patch fixes the recording of these instructions.
|
||||
|
||||
gdb/ChangeLog:
|
||||
|
||||
PR tdep/26916
|
||||
* s390-tdep.c (s390_process_record): Fix recording of STOC, STOCG,
|
||||
and STOCFH.
|
||||
|
||||
diff --git a/gdb/s390-tdep.c b/gdb/s390-tdep.c
|
||||
--- a/gdb/s390-tdep.c
|
||||
+++ b/gdb/s390-tdep.c
|
||||
@@ -5380,7 +5380,6 @@ ex:
|
||||
case 0xe325: /* NTSTG - nontransactional store */
|
||||
case 0xe326: /* CVDY - convert to decimal */
|
||||
case 0xe32f: /* STRVG - store reversed */
|
||||
- case 0xebe3: /* STOCG - store on condition */
|
||||
case 0xed67: /* STDY - store */
|
||||
oaddr = s390_record_calc_disp (gdbarch, regcache, inib[3], insn[1], ibyte[4]);
|
||||
if (record_full_arch_list_add_mem (oaddr, 8))
|
||||
@@ -5409,8 +5408,6 @@ ex:
|
||||
case 0xe33e: /* STRV - store reversed */
|
||||
case 0xe350: /* STY - store */
|
||||
case 0xe3cb: /* STFH - store high */
|
||||
- case 0xebe1: /* STOCFH - store high on condition */
|
||||
- case 0xebf3: /* STOC - store on condition */
|
||||
case 0xed66: /* STEY - store */
|
||||
oaddr = s390_record_calc_disp (gdbarch, regcache, inib[3], insn[1], ibyte[4]);
|
||||
if (record_full_arch_list_add_mem (oaddr, 4))
|
||||
@@ -6123,6 +6120,20 @@ ex:
|
||||
|
||||
/* 0xeb9c-0xebbf undefined */
|
||||
/* 0xebc1-0xebdb undefined */
|
||||
+
|
||||
+ case 0xebe1: /* STOCFH - store high on condition */
|
||||
+ case 0xebf3: /* STOC - store on condition */
|
||||
+ oaddr = s390_record_calc_disp (gdbarch, regcache, 0, insn[1], ibyte[4]);
|
||||
+ if (record_full_arch_list_add_mem (oaddr, 4))
|
||||
+ return -1;
|
||||
+ break;
|
||||
+
|
||||
+ case 0xebe3: /* STOCG - store on condition */
|
||||
+ oaddr = s390_record_calc_disp (gdbarch, regcache, 0, insn[1], ibyte[4]);
|
||||
+ if (record_full_arch_list_add_mem (oaddr, 8))
|
||||
+ return -1;
|
||||
+ break;
|
||||
+
|
||||
/* 0xebe5 undefined */
|
||||
/* 0xebe9 undefined */
|
||||
/* 0xebeb-0xebf1 undefined */
|
565
SOURCES/gdb-rhbz1905702-DWARF-data_location.patch
Normal file
565
SOURCES/gdb-rhbz1905702-DWARF-data_location.patch
Normal file
@ -0,0 +1,565 @@
|
||||
From FEDORA_PATCHES Mon Sep 17 00:00:00 2001
|
||||
From: Keith Seitz <keiths@redhat.com>
|
||||
Date: Wed, 9 Dec 2020 16:47:07 -0500
|
||||
Subject: gdb-rhbz1905702-DWARF-data_location.patch
|
||||
|
||||
;; Backport "fortran dynamic type related fixes"
|
||||
;; Andrew Burgess (RH BZ 1905702)
|
||||
|
||||
commit e79eb02f2f09baecffb144bac6804f975065466f
|
||||
|
||||
gdb/fortran: resolve dynamic types when readjusting after an indirection
|
||||
|
||||
After dereferencing a pointer (in value_ind) or following a
|
||||
reference (in coerce_ref) we call readjust_indirect_value_type to
|
||||
"fixup" the type of the resulting value object.
|
||||
|
||||
This fixup handles cases relating to the type of the resulting object
|
||||
being different (a sub-class) of the original pointers target type.
|
||||
|
||||
If we encounter a pointer to a dynamic type then after dereferencing a
|
||||
pointer (in value_ind) the type of the object created will have had
|
||||
its dynamic type resolved. However, in readjust_indirect_value_type,
|
||||
we use the target type of the original pointer to "fixup" the type of
|
||||
the resulting value. In this case, the target type will be a dynamic
|
||||
type, so the resulting value object, once again has a dynamic type.
|
||||
|
||||
This then triggers an assertion later within GDB.
|
||||
|
||||
The solution I propose here is that we call resolve_dynamic_type on
|
||||
the pointer's target type (within readjust_indirect_value_type) so
|
||||
that the resulting value is not converted back to a dynamic type.
|
||||
|
||||
The test case is based on the original test in the bug report.
|
||||
|
||||
gdb/ChangeLog:
|
||||
|
||||
PR fortran/23051
|
||||
PR fortran/26139
|
||||
* valops.c (value_ind): Pass address to
|
||||
readjust_indirect_value_type.
|
||||
* value.c (readjust_indirect_value_type): Make parameter
|
||||
non-const, and add extra address parameter. Resolve original type
|
||||
before using it.
|
||||
* value.h (readjust_indirect_value_type): Update function
|
||||
signature and comment.
|
||||
|
||||
gdb/testsuite/ChangeLog:
|
||||
|
||||
PR fortran/23051
|
||||
PR fortran/26139
|
||||
* gdb.fortran/class-allocatable-array.exp: New file.
|
||||
* gdb.fortran/class-allocatable-array.f90: New file.
|
||||
* gdb.fortran/pointer-to-pointer.exp: New file.
|
||||
* gdb.fortran/pointer-to-pointer.f90: New file.
|
||||
|
||||
diff --git a/gdb/testsuite/gdb.dwarf2/graalvm-data-loc2.c b/gdb/testsuite/gdb.dwarf2/graalvm-data-loc2.c
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
+++ b/gdb/testsuite/gdb.dwarf2/graalvm-data-loc2.c
|
||||
@@ -0,0 +1,63 @@
|
||||
+/* Copyright 2014-2020 Free Software Foundation, Inc.
|
||||
+
|
||||
+ This file is part of GDB.
|
||||
+
|
||||
+ 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/>. */
|
||||
+
|
||||
+/* This C file simulates the implementation of object pointers in
|
||||
+ GraalVM Java native images where the object data is not addressed
|
||||
+ directly. It serves as a regression test for a bug where printing
|
||||
+ of such redirected data structures suffers from a gdb exception.
|
||||
+
|
||||
+ Debugging information on how to decode an object pointer to
|
||||
+ identify the address of the underlying data will be generated
|
||||
+ separately by the testcase using that file. */
|
||||
+
|
||||
+#include <stdlib.h>
|
||||
+#include <string.h>
|
||||
+
|
||||
+struct Object {
|
||||
+ struct Object *next;
|
||||
+ int val;
|
||||
+};
|
||||
+
|
||||
+struct Object *testOop;
|
||||
+
|
||||
+extern int debugMe() {
|
||||
+ return 0;
|
||||
+}
|
||||
+
|
||||
+struct Object *newObject() {
|
||||
+ char *bytes = malloc(sizeof(struct Object));
|
||||
+ return (struct Object *)bytes;
|
||||
+}
|
||||
+
|
||||
+int
|
||||
+main (void)
|
||||
+{
|
||||
+ struct Object *obj1 = newObject();
|
||||
+ struct Object *obj2 = newObject();
|
||||
+ struct Object *obj3 = newObject();
|
||||
+ obj1->val = 0;
|
||||
+ obj2->val = 1;
|
||||
+ obj3->val = 2;
|
||||
+
|
||||
+ obj1->next = obj2;
|
||||
+ obj2->next = obj3;
|
||||
+ obj3->next = obj1;
|
||||
+
|
||||
+ testOop = obj1;
|
||||
+
|
||||
+ return debugMe();
|
||||
+}
|
||||
diff --git a/gdb/testsuite/gdb.dwarf2/graalvm-data-loc2.exp b/gdb/testsuite/gdb.dwarf2/graalvm-data-loc2.exp
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
+++ b/gdb/testsuite/gdb.dwarf2/graalvm-data-loc2.exp
|
||||
@@ -0,0 +1,122 @@
|
||||
+# Copyright 2014-2020 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/>.
|
||||
+load_lib dwarf.exp
|
||||
+
|
||||
+# This test can only be run on targets which support DWARF-2 and use gas.
|
||||
+if {![dwarf2_support]} {
|
||||
+ return 0
|
||||
+}
|
||||
+
|
||||
+standard_testfile .c -dw.S
|
||||
+
|
||||
+if { [prepare_for_testing "failed to prepare" ${testfile} ${srcfile}] } {
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+# Make some DWARF for the test.
|
||||
+set asm_file [standard_output_file $srcfile2]
|
||||
+Dwarf::assemble $asm_file {
|
||||
+
|
||||
+ cu {} {
|
||||
+ DW_TAG_compile_unit {
|
||||
+ {DW_AT_language @DW_LANG_C99}
|
||||
+ {DW_AT_name data-loc2.c}
|
||||
+ {DW_AT_comp_dir /tmp}
|
||||
+ } {
|
||||
+ declare_labels integer_label struct_label pointer_label
|
||||
+
|
||||
+ integer_label: DW_TAG_base_type {
|
||||
+ {DW_AT_byte_size 4 DW_FORM_sdata}
|
||||
+ {DW_AT_encoding @DW_ATE_signed}
|
||||
+ {DW_AT_name integer}
|
||||
+ }
|
||||
+
|
||||
+ struct_label: DW_TAG_structure_type {
|
||||
+ {DW_AT_name "Object"}
|
||||
+ {DW_AT_byte_size 20 DW_FORM_sdata}
|
||||
+ {DW_AT_data_location {
|
||||
+ DW_OP_push_object_address
|
||||
+ } SPECIAL_expr}
|
||||
+ } {
|
||||
+ member {
|
||||
+ {name next}
|
||||
+ {type :$pointer_label}
|
||||
+ {data_member_location 0 data1}
|
||||
+ }
|
||||
+ member {
|
||||
+ {name val}
|
||||
+ {type :$integer_label}
|
||||
+ {data_member_location 8 data1}
|
||||
+ }
|
||||
+ }
|
||||
+ pointer_label: DW_TAG_pointer_type {
|
||||
+ {DW_AT_byte_size 4 DW_FORM_sdata}
|
||||
+ {DW_AT_type :$struct_label}
|
||||
+ }
|
||||
+ DW_TAG_variable {
|
||||
+ {DW_AT_name testOop}
|
||||
+ {DW_AT_type :$pointer_label}
|
||||
+ {DW_AT_location {
|
||||
+ DW_OP_addr [gdb_target_symbol testOop]
|
||||
+ } SPECIAL_expr}
|
||||
+ {external 1 flag}
|
||||
+ }
|
||||
+ }
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
+# Now that we've generated the DWARF debugging info, rebuild our
|
||||
+# program using our debug info instead of the info generated by
|
||||
+# the compiler.
|
||||
+
|
||||
+if { [prepare_for_testing "failed to prepare" ${testfile} \
|
||||
+ [list $srcfile $asm_file] {nodebug}] } {
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+if ![runto_main] {
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+# ensure the object network is set up as expected and check that
|
||||
+# printing of structs which employ the data_location does not
|
||||
+# fail with a gdb exception
|
||||
+
|
||||
+gdb_test "break debugMe" \
|
||||
+ "Breakpoint .*" \
|
||||
+ "set breakpoint at debugMe"
|
||||
+
|
||||
+gdb_continue_to_breakpoint "continue to debugMe"
|
||||
+
|
||||
+gdb_test "print testOop->val" \
|
||||
+ ".* = 0"
|
||||
+
|
||||
+gdb_test "print testOop->next->val" \
|
||||
+ ".* = 1"
|
||||
+
|
||||
+gdb_test "print testOop->next->next->val" \
|
||||
+ ".* = 2"
|
||||
+
|
||||
+gdb_test "print *testOop" \
|
||||
+ ".* = {next = .*, val = 0}" \
|
||||
+ "print contents of struct"
|
||||
+
|
||||
+gdb_test "print *testOop->next" \
|
||||
+ ".* = {next = .*, val = 1}" \
|
||||
+ "print contents of an indirect struct"
|
||||
+
|
||||
+gdb_test "print *testOop->next->next" \
|
||||
+ ".* = {next = .*, val = 2}" \
|
||||
+ "print contents of a double indirect struct"
|
||||
diff --git a/gdb/testsuite/gdb.fortran/class-allocatable-array.exp b/gdb/testsuite/gdb.fortran/class-allocatable-array.exp
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
+++ b/gdb/testsuite/gdb.fortran/class-allocatable-array.exp
|
||||
@@ -0,0 +1,43 @@
|
||||
+# Copyright 2020 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/> .
|
||||
+
|
||||
+# Test that GDB can print an allocatable array that is a data field
|
||||
+# within a class like type.
|
||||
+
|
||||
+if {[skip_fortran_tests]} { return -1 }
|
||||
+
|
||||
+standard_testfile ".f90"
|
||||
+load_lib fortran.exp
|
||||
+
|
||||
+if {[prepare_for_testing ${testfile}.exp ${testfile} ${srcfile} \
|
||||
+ {debug f90}]} {
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+if {![runto MAIN__]} {
|
||||
+ untested main"could not run to main"
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+gdb_breakpoint [gdb_get_line_number "Break Here"]
|
||||
+gdb_continue_to_breakpoint "Break Here"
|
||||
+
|
||||
+# If this first test fails then the Fortran compiler being used uses
|
||||
+# different names, or maybe a completely different approach, for
|
||||
+# representing class like structures. The following tests are
|
||||
+# cetainly going to fail.
|
||||
+gdb_test "print this" " = \\( _data = \[^\r\n\]+, _vptr = \[^\r\n\]+\\)"
|
||||
+gdb_test "print this%_data" " = \\(PTR TO -> \\( Type test_type \\)\\) \[^\r\n\]+"
|
||||
+gdb_test "print this%_data%b" " = \\(\\( 1, 2, 3\\) \\( 4, 5, 6\\) \\)"
|
||||
diff --git a/gdb/testsuite/gdb.fortran/class-allocatable-array.f90 b/gdb/testsuite/gdb.fortran/class-allocatable-array.f90
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
+++ b/gdb/testsuite/gdb.fortran/class-allocatable-array.f90
|
||||
@@ -0,0 +1,54 @@
|
||||
+! Copyright 2020 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/>.
|
||||
+
|
||||
+module test_module
|
||||
+ type test_type
|
||||
+ integer a
|
||||
+ real, allocatable :: b (:, :)
|
||||
+ contains
|
||||
+ procedure :: test_proc
|
||||
+ end type test_type
|
||||
+
|
||||
+contains
|
||||
+
|
||||
+ subroutine test_proc (this)
|
||||
+ class(test_type), intent (inout) :: this
|
||||
+ allocate (this%b (3, 2))
|
||||
+ call fill_array_2d (this%b)
|
||||
+ print *, "" ! Break Here
|
||||
+ contains
|
||||
+ ! Helper subroutine to fill 2-dimensional array with unique
|
||||
+ ! values.
|
||||
+ subroutine fill_array_2d (array)
|
||||
+ real, dimension (:,:) :: array
|
||||
+ real :: counter
|
||||
+
|
||||
+ counter = 1.0
|
||||
+ do i=LBOUND (array, 2), UBOUND (array, 2), 1
|
||||
+ do j=LBOUND (array, 1), UBOUND (array, 1), 1
|
||||
+ array (j,i) = counter
|
||||
+ counter = counter + 1
|
||||
+ end do
|
||||
+ end do
|
||||
+ end subroutine fill_array_2d
|
||||
+ end subroutine test_proc
|
||||
+end module
|
||||
+
|
||||
+program test
|
||||
+ use test_module
|
||||
+ implicit none
|
||||
+ type(test_type) :: t
|
||||
+ call t%test_proc ()
|
||||
+end program test
|
||||
diff --git a/gdb/testsuite/gdb.fortran/pointer-to-pointer.exp b/gdb/testsuite/gdb.fortran/pointer-to-pointer.exp
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
+++ b/gdb/testsuite/gdb.fortran/pointer-to-pointer.exp
|
||||
@@ -0,0 +1,46 @@
|
||||
+# Copyright 2020 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/> .
|
||||
+
|
||||
+# Test for GDB printing a pointer to a type containing a buffer.
|
||||
+
|
||||
+if {[skip_fortran_tests]} { return -1 }
|
||||
+
|
||||
+standard_testfile ".f90"
|
||||
+load_lib fortran.exp
|
||||
+
|
||||
+if {[prepare_for_testing ${testfile}.exp ${testfile} ${srcfile} \
|
||||
+ {debug f90}]} {
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+if {![runto MAIN__]} {
|
||||
+ untested "could not run to main"
|
||||
+ return -1
|
||||
+}
|
||||
+
|
||||
+gdb_breakpoint [gdb_get_line_number "Break Here"]
|
||||
+gdb_continue_to_breakpoint "Break Here"
|
||||
+
|
||||
+gdb_test "print *buffer" \
|
||||
+ " = \\( alpha = \\(1\\.5, 2\\.5, 3\\.5, 4\\.5, 5\\.5\\) \\)"
|
||||
+
|
||||
+set l_buffer_type [multi_line \
|
||||
+ "Type l_buffer" \
|
||||
+ " real\\(kind=4\\) :: alpha\\(.\\)" \
|
||||
+ "End Type l_buffer" ]
|
||||
+
|
||||
+gdb_test "ptype buffer" "type = PTR TO -> \\( ${l_buffer_type} \\)"
|
||||
+gdb_test "ptype *buffer" "type = ${l_buffer_type}"
|
||||
+gdb_test "ptype buffer%alpha" "type = real\\(kind=4\\) \\(5\\)"
|
||||
diff --git a/gdb/testsuite/gdb.fortran/pointer-to-pointer.f90 b/gdb/testsuite/gdb.fortran/pointer-to-pointer.f90
|
||||
new file mode 100644
|
||||
--- /dev/null
|
||||
+++ b/gdb/testsuite/gdb.fortran/pointer-to-pointer.f90
|
||||
@@ -0,0 +1,34 @@
|
||||
+! Copyright 2020 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/>.
|
||||
+
|
||||
+program allocate_array
|
||||
+
|
||||
+ type l_buffer
|
||||
+ real, dimension(:), pointer :: alpha
|
||||
+ end type l_buffer
|
||||
+ type(l_buffer), pointer :: buffer
|
||||
+
|
||||
+ allocate (buffer)
|
||||
+ allocate (buffer%alpha (5))
|
||||
+
|
||||
+ buffer%alpha (1) = 1.5
|
||||
+ buffer%alpha (2) = 2.5
|
||||
+ buffer%alpha (3) = 3.5
|
||||
+ buffer%alpha (4) = 4.5
|
||||
+ buffer%alpha (5) = 5.5
|
||||
+
|
||||
+ print *, buffer%alpha ! Break Here.
|
||||
+
|
||||
+end program allocate_array
|
||||
diff --git a/gdb/valops.c b/gdb/valops.c
|
||||
--- a/gdb/valops.c
|
||||
+++ b/gdb/valops.c
|
||||
@@ -1553,38 +1553,28 @@ value_ind (struct value *arg1)
|
||||
if (TYPE_CODE (base_type) == TYPE_CODE_PTR)
|
||||
{
|
||||
struct type *enc_type;
|
||||
- CORE_ADDR addr;
|
||||
-
|
||||
- if (type_not_associated (base_type))
|
||||
- error (_("Attempt to take contents of a not associated pointer."));
|
||||
-
|
||||
- if (NULL != TYPE_DATA_LOCATION (TYPE_TARGET_TYPE (base_type)))
|
||||
- addr = value_address (arg1);
|
||||
- else
|
||||
- addr = value_as_address (arg1);
|
||||
-
|
||||
- if (addr != 0)
|
||||
- TYPE_TARGET_TYPE (base_type) =
|
||||
- resolve_dynamic_type (TYPE_TARGET_TYPE (base_type), NULL, addr);
|
||||
|
||||
/* We may be pointing to something embedded in a larger object.
|
||||
Get the real type of the enclosing object. */
|
||||
enc_type = check_typedef (value_enclosing_type (arg1));
|
||||
enc_type = TYPE_TARGET_TYPE (enc_type);
|
||||
|
||||
+ CORE_ADDR base_addr;
|
||||
if (TYPE_CODE (check_typedef (enc_type)) == TYPE_CODE_FUNC
|
||||
|| TYPE_CODE (check_typedef (enc_type)) == TYPE_CODE_METHOD)
|
||||
/* For functions, go through find_function_addr, which knows
|
||||
how to handle function descriptors. */
|
||||
- arg2 = value_at_lazy (enc_type,
|
||||
- find_function_addr (arg1, NULL));
|
||||
+ base_addr = find_function_addr (arg1, NULL);
|
||||
else
|
||||
- /* Retrieve the enclosing object pointed to. */
|
||||
- arg2 = value_at_lazy (enc_type,
|
||||
- (addr - value_pointed_to_offset (arg1)));
|
||||
-
|
||||
+ {
|
||||
+ /* Retrieve the enclosing object pointed to. */
|
||||
+ base_addr = (value_as_address (arg1)
|
||||
+ - value_pointed_to_offset (arg1));
|
||||
+ }
|
||||
+ arg2 = value_at_lazy (enc_type, base_addr);
|
||||
enc_type = value_type (arg2);
|
||||
- return readjust_indirect_value_type (arg2, enc_type, base_type, arg1);
|
||||
+ return readjust_indirect_value_type (arg2, enc_type, base_type,
|
||||
+ arg1, base_addr);
|
||||
}
|
||||
|
||||
error (_("Attempt to take contents of a non-pointer value."));
|
||||
diff --git a/gdb/value.c b/gdb/value.c
|
||||
--- a/gdb/value.c
|
||||
+++ b/gdb/value.c
|
||||
@@ -3630,10 +3630,19 @@ coerce_ref_if_computed (const struct value *arg)
|
||||
struct value *
|
||||
readjust_indirect_value_type (struct value *value, struct type *enc_type,
|
||||
const struct type *original_type,
|
||||
- const struct value *original_value)
|
||||
+ struct value *original_value,
|
||||
+ CORE_ADDR original_value_address)
|
||||
{
|
||||
+ gdb_assert (TYPE_CODE (original_type) == TYPE_CODE_PTR
|
||||
+ || TYPE_IS_REFERENCE (original_type));
|
||||
+
|
||||
+ struct type *original_target_type = TYPE_TARGET_TYPE (original_type);
|
||||
+ struct type *resolved_original_target_type
|
||||
+ = resolve_dynamic_type (original_target_type, NULL,
|
||||
+ original_value_address);
|
||||
+
|
||||
/* Re-adjust type. */
|
||||
- deprecated_set_value_type (value, TYPE_TARGET_TYPE (original_type));
|
||||
+ deprecated_set_value_type (value, resolved_original_target_type);
|
||||
|
||||
/* Add embedding info. */
|
||||
set_value_enclosing_type (value, enc_type);
|
||||
@@ -3660,12 +3669,11 @@ coerce_ref (struct value *arg)
|
||||
enc_type = check_typedef (value_enclosing_type (arg));
|
||||
enc_type = TYPE_TARGET_TYPE (enc_type);
|
||||
|
||||
- retval = value_at_lazy (enc_type,
|
||||
- unpack_pointer (value_type (arg),
|
||||
- value_contents (arg)));
|
||||
+ CORE_ADDR addr = unpack_pointer (value_type (arg), value_contents (arg));
|
||||
+ retval = value_at_lazy (enc_type, addr);
|
||||
enc_type = value_type (retval);
|
||||
- return readjust_indirect_value_type (retval, enc_type,
|
||||
- value_type_arg_tmp, arg);
|
||||
+ return readjust_indirect_value_type (retval, enc_type, value_type_arg_tmp,
|
||||
+ arg, addr);
|
||||
}
|
||||
|
||||
struct value *
|
||||
diff --git a/gdb/value.h b/gdb/value.h
|
||||
--- a/gdb/value.h
|
||||
+++ b/gdb/value.h
|
||||
@@ -488,7 +488,9 @@ extern struct value *coerce_ref_if_computed (const struct value *arg);
|
||||
|
||||
/* Setup a new value type and enclosing value type for dereferenced value VALUE.
|
||||
ENC_TYPE is the new enclosing type that should be set. ORIGINAL_TYPE and
|
||||
- ORIGINAL_VAL are the type and value of the original reference or pointer.
|
||||
+ ORIGINAL_VAL are the type and value of the original reference or
|
||||
+ pointer. ORIGINAL_VALUE_ADDRESS is the address within VALUE, that is
|
||||
+ the address that was dereferenced.
|
||||
|
||||
Note, that VALUE is modified by this function.
|
||||
|
||||
@@ -497,7 +499,8 @@ extern struct value *coerce_ref_if_computed (const struct value *arg);
|
||||
extern struct value * readjust_indirect_value_type (struct value *value,
|
||||
struct type *enc_type,
|
||||
const struct type *original_type,
|
||||
- const struct value *original_val);
|
||||
+ struct value *original_val,
|
||||
+ CORE_ADDR original_value_address);
|
||||
|
||||
/* Convert a REF to the object referenced. */
|
||||
|
@ -34,7 +34,7 @@ Version: 9.2
|
||||
|
||||
# The release always contains a leading reserved number, start it at 1.
|
||||
# `upstream' is not a part of `name' to stay fully rpm dependencies compatible for the testing.
|
||||
Release: 2%{?dist}
|
||||
Release: 4%{?dist}
|
||||
|
||||
License: GPLv3+ and GPLv3+ with exceptions and GPLv2+ and GPLv2+ with exceptions and GPL+ and LGPLv2+ and LGPLv3+ and BSD and Public Domain and GFDL
|
||||
# Do not provide URL for snapshots as the file lasts there only for 2 days.
|
||||
@ -1167,6 +1167,20 @@ fi
|
||||
%endif
|
||||
|
||||
%changelog
|
||||
* Fri Dec 11 2020 Keith Seitz <keiths@redhat.com> - 9.2-4
|
||||
- Backport "Correct recording of 'store on condition' insns"
|
||||
(Andreas Arnaz, RH BZ 1903375)
|
||||
- Backport "Fortran dynamic type related fixes"
|
||||
(Andrew Burgess, RH BZ 1905702)
|
||||
|
||||
* Mon Nov 16 2020 Keith Seitz <keiths@redhat.com> - 9.2-3
|
||||
- Fix missing debuginfo messages. (Keith Seitz, RH BZ 1894703)
|
||||
- Add debuginfod.m4 patch to use pkg-config.
|
||||
- Backport "Corefile memory access problems" patches.
|
||||
(Kevin Buettner, RH BZ 1886602)
|
||||
- Backport "Exclude debuginfo files from 'outside ELF segments' warning".
|
||||
(Keith Seitz, RH BZ 1898252)
|
||||
|
||||
* Tue Jun 9 2020 Keith Seitz <keiths@redhat.com> - 9.2-2
|
||||
- Backport debuginfod support.
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user